1 /* 2 * Copyright (c) 1991, 1993 3 * The Regents of the University of California. All rights reserved. 4 * 5 * This code is derived from software contributed to Berkeley by 6 * The Mach Operating System project at Carnegie-Mellon University. 7 * 8 * Redistribution and use in source and binary forms, with or without 9 * modification, are permitted provided that the following conditions 10 * are met: 11 * 1. Redistributions of source code must retain the above copyright 12 * notice, this list of conditions and the following disclaimer. 13 * 2. Redistributions in binary form must reproduce the above copyright 14 * notice, this list of conditions and the following disclaimer in the 15 * documentation and/or other materials provided with the distribution. 16 * 3. All advertising materials mentioning features or use of this software 17 * must display the following acknowledgement: 18 * This product includes software developed by the University of 19 * California, Berkeley and its contributors. 20 * 4. Neither the name of the University nor the names of its contributors 21 * may be used to endorse or promote products derived from this software 22 * without specific prior written permission. 23 * 24 * THIS SOFTWARE IS PROVIDED BY THE REGENTS AND CONTRIBUTORS ``AS IS'' AND 25 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 26 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 27 * ARE DISCLAIMED. IN NO EVENT SHALL THE REGENTS OR CONTRIBUTORS BE LIABLE 28 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 29 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 30 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 31 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 32 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 33 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 34 * SUCH DAMAGE. 35 * 36 * from: @(#)vm_object.c 8.5 (Berkeley) 3/22/94 37 * 38 * 39 * Copyright (c) 1987, 1990 Carnegie-Mellon University. 40 * All rights reserved. 41 * 42 * Authors: Avadis Tevanian, Jr., Michael Wayne Young 43 * 44 * Permission to use, copy, modify and distribute this software and 45 * its documentation is hereby granted, provided that both the copyright 46 * notice and this permission notice appear in all copies of the 47 * software, derivative works or modified versions, and any portions 48 * thereof, and that both notices appear in supporting documentation. 49 * 50 * CARNEGIE MELLON ALLOWS FREE USE OF THIS SOFTWARE IN ITS "AS IS" 51 * CONDITION. CARNEGIE MELLON DISCLAIMS ANY LIABILITY OF ANY KIND 52 * FOR ANY DAMAGES WHATSOEVER RESULTING FROM THE USE OF THIS SOFTWARE. 53 * 54 * Carnegie Mellon requests users of this software to return to 55 * 56 * Software Distribution Coordinator or Software.Distribution@CS.CMU.EDU 57 * School of Computer Science 58 * Carnegie Mellon University 59 * Pittsburgh PA 15213-3890 60 * 61 * any improvements or extensions that they make and grant Carnegie the 62 * rights to redistribute these changes. 63 * 64 * $Id: vm_object.c,v 1.26 1995/02/22 09:15:28 davidg Exp $ 65 */ 66 67 /* 68 * Virtual memory object module. 69 */ 70 71 #include <sys/param.h> 72 #include <sys/systm.h> 73 #include <sys/kernel.h> 74 #include <sys/proc.h> /* for curproc, pageproc */ 75 #include <sys/malloc.h> 76 #include <sys/vnode.h> 77 #include <sys/mount.h> 78 79 #include <vm/vm.h> 80 #include <vm/vm_page.h> 81 #include <vm/vm_pageout.h> 82 #include <vm/vm_pager.h> 83 #include <vm/swap_pager.h> 84 #include <vm/vnode_pager.h> 85 #include <vm/vm_kern.h> 86 87 static void _vm_object_allocate(vm_size_t, vm_object_t); 88 89 /* 90 * Virtual memory objects maintain the actual data 91 * associated with allocated virtual memory. A given 92 * page of memory exists within exactly one object. 93 * 94 * An object is only deallocated when all "references" 95 * are given up. Only one "reference" to a given 96 * region of an object should be writeable. 97 * 98 * Associated with each object is a list of all resident 99 * memory pages belonging to that object; this list is 100 * maintained by the "vm_page" module, and locked by the object's 101 * lock. 102 * 103 * Each object also records a "pager" routine which is 104 * used to retrieve (and store) pages to the proper backing 105 * storage. In addition, objects may be backed by other 106 * objects from which they were virtual-copied. 107 * 108 * The only items within the object structure which are 109 * modified after time of creation are: 110 * reference count locked by object's lock 111 * pager routine locked by object's lock 112 * 113 */ 114 115 116 struct vm_object kernel_object_store; 117 struct vm_object kmem_object_store; 118 119 int vm_object_cache_max; 120 121 #define VM_OBJECT_HASH_COUNT 509 122 123 struct vm_object_hash_head vm_object_hashtable[VM_OBJECT_HASH_COUNT]; 124 125 long object_collapses = 0; 126 long object_bypasses = 0; 127 128 static void 129 _vm_object_allocate(size, object) 130 vm_size_t size; 131 register vm_object_t object; 132 { 133 TAILQ_INIT(&object->memq); 134 TAILQ_INIT(&object->reverse_shadow_head); 135 136 object->size = size; 137 object->ref_count = 1; 138 vm_object_lock_init(object); 139 object->flags = OBJ_INTERNAL; /* vm_allocate_with_pager will reset */ 140 object->paging_in_progress = 0; 141 object->resident_page_count = 0; 142 143 object->pager = NULL; 144 object->paging_offset = 0; 145 object->shadow = NULL; 146 object->shadow_offset = (vm_offset_t) 0; 147 object->copy = NULL; 148 149 object->last_read = 0; 150 151 simple_lock(&vm_object_list_lock); 152 TAILQ_INSERT_TAIL(&vm_object_list, object, object_list); 153 vm_object_count++; 154 cnt.v_nzfod += atop(size); 155 simple_unlock(&vm_object_list_lock); 156 } 157 158 /* 159 * vm_object_init: 160 * 161 * Initialize the VM objects module. 162 */ 163 void 164 vm_object_init(vm_offset_t nothing) 165 { 166 register int i; 167 168 TAILQ_INIT(&vm_object_cached_list); 169 TAILQ_INIT(&vm_object_list); 170 vm_object_count = 0; 171 simple_lock_init(&vm_cache_lock); 172 simple_lock_init(&vm_object_list_lock); 173 174 vm_object_cache_max = 84; 175 if (cnt.v_page_count > 1000) 176 vm_object_cache_max += (cnt.v_page_count - 1000) / 4; 177 178 for (i = 0; i < VM_OBJECT_HASH_COUNT; i++) 179 TAILQ_INIT(&vm_object_hashtable[i]); 180 181 kernel_object = &kernel_object_store; 182 _vm_object_allocate(VM_MAX_KERNEL_ADDRESS - VM_MIN_KERNEL_ADDRESS, 183 kernel_object); 184 185 kmem_object = &kmem_object_store; 186 _vm_object_allocate(VM_MAX_KERNEL_ADDRESS - VM_MIN_KERNEL_ADDRESS, 187 kmem_object); 188 } 189 190 /* 191 * vm_object_allocate: 192 * 193 * Returns a new object with the given size. 194 */ 195 196 vm_object_t 197 vm_object_allocate(size) 198 vm_size_t size; 199 { 200 register vm_object_t result; 201 202 result = (vm_object_t) 203 malloc((u_long) sizeof *result, M_VMOBJ, M_WAITOK); 204 205 206 _vm_object_allocate(size, result); 207 208 return (result); 209 } 210 211 212 /* 213 * vm_object_reference: 214 * 215 * Gets another reference to the given object. 216 */ 217 inline void 218 vm_object_reference(object) 219 register vm_object_t object; 220 { 221 if (object == NULL) 222 return; 223 224 vm_object_lock(object); 225 object->ref_count++; 226 vm_object_unlock(object); 227 } 228 229 /* 230 * vm_object_deallocate: 231 * 232 * Release a reference to the specified object, 233 * gained either through a vm_object_allocate 234 * or a vm_object_reference call. When all references 235 * are gone, storage associated with this object 236 * may be relinquished. 237 * 238 * No object may be locked. 239 */ 240 void 241 vm_object_deallocate(object) 242 vm_object_t object; 243 { 244 vm_object_t temp; 245 246 while (object != NULL) { 247 248 if (object->ref_count == 0) 249 panic("vm_object_deallocate: object deallocated too many times"); 250 251 /* 252 * The cache holds a reference (uncounted) to the object; we 253 * must lock it before removing the object. 254 */ 255 256 vm_object_cache_lock(); 257 258 /* 259 * Lose the reference 260 */ 261 vm_object_lock(object); 262 if (--(object->ref_count) != 0) { 263 if (object->ref_count == 1) { 264 vm_object_t robject; 265 robject = object->reverse_shadow_head.tqh_first; 266 if( robject) { 267 int s; 268 robject->ref_count += 2; 269 object->ref_count += 2; 270 271 do { 272 s = splhigh(); 273 while (robject->paging_in_progress) { 274 robject->flags |= OBJ_PIPWNT; 275 tsleep(robject, PVM, "objde1", 0); 276 } 277 278 while (object->paging_in_progress) { 279 object->flags |= OBJ_PIPWNT; 280 tsleep(object, PVM, "objde2", 0); 281 } 282 splx(s); 283 284 } while( object->paging_in_progress || robject->paging_in_progress); 285 286 object->ref_count -= 2; 287 robject->ref_count -= 2; 288 if( robject->ref_count == 0) { 289 vm_object_unlock(object); 290 vm_object_cache_unlock(); 291 robject->ref_count += 1; 292 object = robject; 293 continue; 294 } 295 vm_object_cache_unlock(); 296 vm_object_unlock(object); 297 vm_object_lock(robject); 298 vm_object_collapse(robject); 299 return; 300 } 301 } 302 vm_object_unlock(object); 303 /* 304 * If there are still references, then we are done. 305 */ 306 vm_object_cache_unlock(); 307 return; 308 } 309 /* 310 * See if this object can persist. If so, enter it in the 311 * cache, then deactivate all of its pages. 312 */ 313 314 if (object->flags & OBJ_CANPERSIST) { 315 316 TAILQ_INSERT_TAIL(&vm_object_cached_list, object, 317 cached_list); 318 vm_object_cached++; 319 vm_object_cache_unlock(); 320 321 vm_object_unlock(object); 322 323 vm_object_cache_trim(); 324 return; 325 } 326 /* 327 * Make sure no one can look us up now. 328 */ 329 object->flags |= OBJ_DEAD; 330 vm_object_remove(object->pager); 331 vm_object_cache_unlock(); 332 333 temp = object->shadow; 334 if (temp) 335 TAILQ_REMOVE(&temp->reverse_shadow_head, object, reverse_shadow_list); 336 vm_object_terminate(object); 337 /* unlocks and deallocates object */ 338 object = temp; 339 } 340 } 341 342 /* 343 * vm_object_terminate actually destroys the specified object, freeing 344 * up all previously used resources. 345 * 346 * The object must be locked. 347 */ 348 void 349 vm_object_terminate(object) 350 register vm_object_t object; 351 { 352 register vm_page_t p, next; 353 vm_object_t shadow_object; 354 int s; 355 struct vnode *vp = NULL; 356 357 /* 358 * Detach the object from its shadow if we are the shadow's copy. 359 */ 360 if ((shadow_object = object->shadow) != NULL) { 361 vm_object_lock(shadow_object); 362 if (shadow_object->copy == object) 363 shadow_object->copy = NULL; 364 /* 365 else if (shadow_object->copy != NULL) 366 panic("vm_object_terminate: copy/shadow inconsistency"); 367 */ 368 vm_object_unlock(shadow_object); 369 } 370 if (object->pager && (object->pager->pg_type == PG_VNODE)) { 371 vn_pager_t vnp = object->pager->pg_data; 372 373 vp = vnp->vnp_vp; 374 VOP_FSYNC(vp, NOCRED, MNT_WAIT, NULL); 375 vinvalbuf(vp, 0, NOCRED, NULL, 0, 0); 376 } 377 /* 378 * Wait until the pageout daemon is through with the object. 379 */ 380 381 s = splhigh(); 382 while (object->paging_in_progress) { 383 vm_object_unlock(object); 384 object->flags |= OBJ_PIPWNT; 385 tsleep((caddr_t) object, PVM, "objtrm", 0); 386 vm_object_lock(object); 387 } 388 splx(s); 389 390 /* 391 * While the paging system is locked, pull the object's pages off the 392 * active and inactive queues. This keeps the pageout daemon from 393 * playing with them during vm_pager_deallocate. 394 * 395 * We can't free the pages yet, because the object's pager may have to 396 * write them out before deallocating the paging space. 397 */ 398 399 for (p = object->memq.tqh_first; p; p = next) { 400 VM_PAGE_CHECK(p); 401 next = p->listq.tqe_next; 402 403 vm_page_lock_queues(); 404 if (p->flags & PG_CACHE) 405 vm_page_free(p); 406 else 407 vm_page_unqueue(p); 408 vm_page_unlock_queues(); 409 p = next; 410 } 411 412 if (object->paging_in_progress != 0) 413 panic("vm_object_deallocate: pageout in progress"); 414 415 /* 416 * Clean and free the pages, as appropriate. All references to the 417 * object are gone, so we don't need to lock it. 418 */ 419 420 if (((object->flags & OBJ_INTERNAL) == 0) && 421 object->pager && (object->pager->pg_type != PG_DEVICE)) { 422 (void) vm_object_page_clean(object, 0, 0, TRUE, TRUE); 423 } 424 /* 425 * one last time -- get rid of buffers that might have been created 426 * for the vm_object_page_clean 427 */ 428 if (vp != NULL) { 429 vm_object_unlock(object); 430 vinvalbuf(vp, 0, NOCRED, NULL, 0, 0); 431 vm_object_lock(object); 432 } 433 /* 434 * Now free the pages. For internal objects, this also removes them 435 * from paging queues. 436 */ 437 while ((p = object->memq.tqh_first) != NULL) { 438 VM_PAGE_CHECK(p); 439 vm_page_lock_queues(); 440 PAGE_WAKEUP(p); 441 vm_page_free(p); 442 cnt.v_pfree++; 443 vm_page_unlock_queues(); 444 } 445 vm_object_unlock(object); 446 447 /* 448 * Let the pager know object is dead. 449 */ 450 if (object->pager != NULL) 451 vm_pager_deallocate(object->pager); 452 453 simple_lock(&vm_object_list_lock); 454 TAILQ_REMOVE(&vm_object_list, object, object_list); 455 vm_object_count--; 456 simple_unlock(&vm_object_list_lock); 457 458 /* 459 * Free the space for the object. 460 */ 461 free((caddr_t) object, M_VMOBJ); 462 } 463 464 /* 465 * vm_object_page_clean 466 * 467 * Clean all dirty pages in the specified range of object. 468 * Leaves page on whatever queue it is currently on. 469 * 470 * Odd semantics: if start == end, we clean everything. 471 * 472 * The object must be locked. 473 */ 474 boolean_t 475 vm_object_page_clean(object, start, end, syncio, de_queue) 476 register vm_object_t object; 477 register vm_offset_t start; 478 register vm_offset_t end; 479 boolean_t syncio; 480 boolean_t de_queue; 481 { 482 register vm_page_t p, nextp; 483 int size; 484 485 if (object->pager == NULL) 486 return 1; 487 488 if (start != end) { 489 start = trunc_page(start); 490 end = round_page(end); 491 } 492 size = end - start; 493 494 again: 495 /* 496 * Wait until the pageout daemon is through with the object. 497 */ 498 while (object->paging_in_progress) { 499 object->flags |= OBJ_PIPWNT; 500 tsleep(object, PVM, "objpcw", 0); 501 } 502 503 nextp = object->memq.tqh_first; 504 while ((p = nextp) && ((start == end) || (size != 0))) { 505 nextp = p->listq.tqe_next; 506 if (start == end || (p->offset >= start && p->offset < end)) { 507 if ((p->flags & PG_BUSY) || p->busy) { 508 int s = splhigh(); 509 510 p->flags |= PG_WANTED; 511 tsleep(p, PVM, "objpcn", 0); 512 splx(s); 513 goto again; 514 } 515 size -= PAGE_SIZE; 516 517 vm_page_test_dirty(p); 518 519 if ((p->dirty & p->valid) != 0) { 520 vm_pageout_clean(p, VM_PAGEOUT_FORCE); 521 goto again; 522 } 523 } 524 } 525 wakeup((caddr_t) object); 526 return 1; 527 } 528 529 /* 530 * vm_object_deactivate_pages 531 * 532 * Deactivate all pages in the specified object. (Keep its pages 533 * in memory even though it is no longer referenced.) 534 * 535 * The object must be locked. 536 */ 537 void 538 vm_object_deactivate_pages(object) 539 register vm_object_t object; 540 { 541 register vm_page_t p, next; 542 543 for (p = object->memq.tqh_first; p != NULL; p = next) { 544 next = p->listq.tqe_next; 545 vm_page_lock_queues(); 546 vm_page_deactivate(p); 547 vm_page_unlock_queues(); 548 } 549 } 550 551 /* 552 * Trim the object cache to size. 553 */ 554 void 555 vm_object_cache_trim() 556 { 557 register vm_object_t object; 558 559 vm_object_cache_lock(); 560 while (vm_object_cached > vm_object_cache_max) { 561 object = vm_object_cached_list.tqh_first; 562 vm_object_cache_unlock(); 563 564 if (object != vm_object_lookup(object->pager)) 565 panic("vm_object_cache_trim: I'm sooo confused."); 566 567 pager_cache(object, FALSE); 568 569 vm_object_cache_lock(); 570 } 571 vm_object_cache_unlock(); 572 } 573 574 575 /* 576 * vm_object_pmap_copy: 577 * 578 * Makes all physical pages in the specified 579 * object range copy-on-write. No writeable 580 * references to these pages should remain. 581 * 582 * The object must *not* be locked. 583 */ 584 void 585 vm_object_pmap_copy(object, start, end) 586 register vm_object_t object; 587 register vm_offset_t start; 588 register vm_offset_t end; 589 { 590 register vm_page_t p; 591 592 if (object == NULL) 593 return; 594 595 vm_object_lock(object); 596 for (p = object->memq.tqh_first; p != NULL; p = p->listq.tqe_next) { 597 if ((start <= p->offset) && (p->offset < end)) { 598 pmap_page_protect(VM_PAGE_TO_PHYS(p), VM_PROT_READ); 599 p->flags |= PG_COPYONWRITE; 600 } 601 } 602 vm_object_unlock(object); 603 } 604 605 /* 606 * vm_object_pmap_remove: 607 * 608 * Removes all physical pages in the specified 609 * object range from all physical maps. 610 * 611 * The object must *not* be locked. 612 */ 613 void 614 vm_object_pmap_remove(object, start, end) 615 register vm_object_t object; 616 register vm_offset_t start; 617 register vm_offset_t end; 618 { 619 register vm_page_t p; 620 int s; 621 622 if (object == NULL) 623 return; 624 ++object->paging_in_progress; 625 626 vm_object_lock(object); 627 again: 628 for (p = object->memq.tqh_first; p != NULL; p = p->listq.tqe_next) { 629 if ((start <= p->offset) && (p->offset < end)) { 630 s = splhigh(); 631 if ((p->flags & PG_BUSY) || p->busy) { 632 p->flags |= PG_WANTED; 633 tsleep((caddr_t) p, PVM, "vmopmr", 0); 634 splx(s); 635 goto again; 636 } 637 splx(s); 638 pmap_page_protect(VM_PAGE_TO_PHYS(p), VM_PROT_NONE); 639 } 640 } 641 vm_object_unlock(object); 642 --object->paging_in_progress; 643 if (object->paging_in_progress == 0 && (object->flags & OBJ_PIPWNT)) { 644 object->flags &= ~OBJ_PIPWNT; 645 wakeup((caddr_t) object); 646 } 647 } 648 649 /* 650 * vm_object_copy: 651 * 652 * Create a new object which is a copy of an existing 653 * object, and mark all of the pages in the existing 654 * object 'copy-on-write'. The new object has one reference. 655 * Returns the new object. 656 * 657 * May defer the copy until later if the object is not backed 658 * up by a non-default pager. 659 */ 660 void 661 vm_object_copy(src_object, src_offset, size, 662 dst_object, dst_offset, src_needs_copy) 663 register vm_object_t src_object; 664 vm_offset_t src_offset; 665 vm_size_t size; 666 vm_object_t *dst_object;/* OUT */ 667 vm_offset_t *dst_offset;/* OUT */ 668 boolean_t *src_needs_copy; /* OUT */ 669 { 670 register vm_object_t new_copy; 671 register vm_object_t old_copy; 672 vm_offset_t new_start, new_end; 673 674 register vm_page_t p; 675 676 if (src_object == NULL) { 677 /* 678 * Nothing to copy 679 */ 680 *dst_object = NULL; 681 *dst_offset = 0; 682 *src_needs_copy = FALSE; 683 return; 684 } 685 /* 686 * If the object's pager is null_pager or the default pager, we don't 687 * have to make a copy of it. Instead, we set the needs copy flag and 688 * make a shadow later. 689 */ 690 691 vm_object_lock(src_object); 692 693 /* 694 * Try to collapse the object before copying it. 695 */ 696 697 vm_object_collapse(src_object); 698 699 if (src_object->pager == NULL || 700 (src_object->flags & OBJ_INTERNAL)) { 701 702 /* 703 * Make another reference to the object 704 */ 705 src_object->ref_count++; 706 707 /* 708 * Mark all of the pages copy-on-write. 709 */ 710 for (p = src_object->memq.tqh_first; p; p = p->listq.tqe_next) 711 if (src_offset <= p->offset && 712 p->offset < src_offset + size) 713 p->flags |= PG_COPYONWRITE; 714 vm_object_unlock(src_object); 715 716 *dst_object = src_object; 717 *dst_offset = src_offset; 718 719 /* 720 * Must make a shadow when write is desired 721 */ 722 *src_needs_copy = TRUE; 723 return; 724 } 725 /* 726 * If the object has a pager, the pager wants to see all of the 727 * changes. We need a copy-object for the changed pages. 728 * 729 * If there is a copy-object, and it is empty, no changes have been made 730 * to the object since the copy-object was made. We can use the same 731 * copy- object. 732 */ 733 734 Retry1: 735 old_copy = src_object->copy; 736 if (old_copy != NULL) { 737 /* 738 * Try to get the locks (out of order) 739 */ 740 if (!vm_object_lock_try(old_copy)) { 741 vm_object_unlock(src_object); 742 743 /* should spin a bit here... */ 744 tsleep((caddr_t) old_copy, PVM, "cpylck", 1); 745 vm_object_lock(src_object); 746 goto Retry1; 747 } 748 if (old_copy->resident_page_count == 0 && 749 old_copy->pager == NULL) { 750 /* 751 * Return another reference to the existing 752 * copy-object. 753 */ 754 old_copy->ref_count++; 755 vm_object_unlock(old_copy); 756 vm_object_unlock(src_object); 757 *dst_object = old_copy; 758 *dst_offset = src_offset; 759 *src_needs_copy = FALSE; 760 return; 761 } 762 vm_object_unlock(old_copy); 763 } 764 vm_object_unlock(src_object); 765 766 /* 767 * If the object has a pager, the pager wants to see all of the 768 * changes. We must make a copy-object and put the changed pages 769 * there. 770 * 771 * The copy-object is always made large enough to completely shadow the 772 * original object, since it may have several users who want to shadow 773 * the original object at different points. 774 */ 775 776 new_copy = vm_object_allocate(src_object->size); 777 778 Retry2: 779 vm_object_lock(src_object); 780 /* 781 * Copy object may have changed while we were unlocked 782 */ 783 old_copy = src_object->copy; 784 if (old_copy != NULL) { 785 /* 786 * Try to get the locks (out of order) 787 */ 788 if (!vm_object_lock_try(old_copy)) { 789 vm_object_unlock(src_object); 790 tsleep((caddr_t) old_copy, PVM, "cpylck", 1); 791 goto Retry2; 792 } 793 /* 794 * Consistency check 795 */ 796 if (old_copy->shadow != src_object || 797 old_copy->shadow_offset != (vm_offset_t) 0) 798 panic("vm_object_copy: copy/shadow inconsistency"); 799 800 /* 801 * Make the old copy-object shadow the new one. It will 802 * receive no more pages from the original object. 803 */ 804 805 src_object->ref_count--; /* remove ref. from old_copy */ 806 if (old_copy->shadow) 807 TAILQ_REMOVE(&old_copy->shadow->reverse_shadow_head, old_copy, reverse_shadow_list); 808 old_copy->shadow = new_copy; 809 TAILQ_INSERT_TAIL(&old_copy->shadow->reverse_shadow_head, old_copy, reverse_shadow_list); 810 new_copy->ref_count++; /* locking not needed - we have the 811 * only pointer */ 812 vm_object_unlock(old_copy); /* done with old_copy */ 813 } 814 new_start = (vm_offset_t) 0; /* always shadow original at 0 */ 815 new_end = (vm_offset_t) new_copy->size; /* for the whole object */ 816 817 /* 818 * Point the new copy at the existing object. 819 */ 820 821 new_copy->shadow = src_object; 822 TAILQ_INSERT_TAIL(&new_copy->shadow->reverse_shadow_head, new_copy, reverse_shadow_list); 823 new_copy->shadow_offset = new_start; 824 src_object->ref_count++; 825 src_object->copy = new_copy; 826 827 /* 828 * Mark all the affected pages of the existing object copy-on-write. 829 */ 830 for (p = src_object->memq.tqh_first; p != NULL; p = p->listq.tqe_next) 831 if ((new_start <= p->offset) && (p->offset < new_end)) 832 p->flags |= PG_COPYONWRITE; 833 834 vm_object_unlock(src_object); 835 836 *dst_object = new_copy; 837 *dst_offset = src_offset - new_start; 838 *src_needs_copy = FALSE; 839 } 840 841 /* 842 * vm_object_shadow: 843 * 844 * Create a new object which is backed by the 845 * specified existing object range. The source 846 * object reference is deallocated. 847 * 848 * The new object and offset into that object 849 * are returned in the source parameters. 850 */ 851 852 void 853 vm_object_shadow(object, offset, length) 854 vm_object_t *object; /* IN/OUT */ 855 vm_offset_t *offset; /* IN/OUT */ 856 vm_size_t length; 857 { 858 register vm_object_t source; 859 register vm_object_t result; 860 861 source = *object; 862 863 /* 864 * Allocate a new object with the given length 865 */ 866 867 if ((result = vm_object_allocate(length)) == NULL) 868 panic("vm_object_shadow: no object for shadowing"); 869 870 /* 871 * The new object shadows the source object, adding a reference to it. 872 * Our caller changes his reference to point to the new object, 873 * removing a reference to the source object. Net result: no change 874 * of reference count. 875 */ 876 result->shadow = source; 877 if (source) 878 TAILQ_INSERT_TAIL(&result->shadow->reverse_shadow_head, result, reverse_shadow_list); 879 880 /* 881 * Store the offset into the source object, and fix up the offset into 882 * the new object. 883 */ 884 885 result->shadow_offset = *offset; 886 887 /* 888 * Return the new things 889 */ 890 891 *offset = 0; 892 *object = result; 893 } 894 895 /* 896 * Set the specified object's pager to the specified pager. 897 */ 898 899 void 900 vm_object_setpager(object, pager, paging_offset, 901 read_only) 902 vm_object_t object; 903 vm_pager_t pager; 904 vm_offset_t paging_offset; 905 boolean_t read_only; 906 { 907 vm_object_lock(object); /* XXX ? */ 908 if (object->pager && object->pager != pager) { 909 panic("!!!pager already allocated!!!\n"); 910 } 911 object->pager = pager; 912 object->paging_offset = paging_offset; 913 vm_object_unlock(object); /* XXX ? */ 914 } 915 916 /* 917 * vm_object_hash hashes the pager/id pair. 918 */ 919 920 #define vm_object_hash(pager) \ 921 (((unsigned)pager >> 5)%VM_OBJECT_HASH_COUNT) 922 923 /* 924 * vm_object_lookup looks in the object cache for an object with the 925 * specified pager and paging id. 926 */ 927 928 vm_object_t 929 vm_object_lookup(pager) 930 vm_pager_t pager; 931 { 932 register vm_object_hash_entry_t entry; 933 vm_object_t object; 934 935 cnt.v_lookups++; 936 vm_object_cache_lock(); 937 938 for (entry = vm_object_hashtable[vm_object_hash(pager)].tqh_first; 939 entry != NULL; 940 entry = entry->hash_links.tqe_next) { 941 object = entry->object; 942 if (object->pager == pager) { 943 vm_object_lock(object); 944 if (object->ref_count == 0) { 945 TAILQ_REMOVE(&vm_object_cached_list, object, 946 cached_list); 947 vm_object_cached--; 948 } 949 object->ref_count++; 950 vm_object_unlock(object); 951 vm_object_cache_unlock(); 952 cnt.v_hits++; 953 return (object); 954 } 955 } 956 957 vm_object_cache_unlock(); 958 return (NULL); 959 } 960 961 /* 962 * vm_object_enter enters the specified object/pager/id into 963 * the hash table. 964 */ 965 966 void 967 vm_object_enter(object, pager) 968 vm_object_t object; 969 vm_pager_t pager; 970 { 971 struct vm_object_hash_head *bucket; 972 register vm_object_hash_entry_t entry; 973 974 /* 975 * We don't cache null objects, and we can't cache objects with the 976 * null pager. 977 */ 978 979 if (object == NULL) 980 return; 981 if (pager == NULL) 982 return; 983 984 bucket = &vm_object_hashtable[vm_object_hash(pager)]; 985 entry = (vm_object_hash_entry_t) 986 malloc((u_long) sizeof *entry, M_VMOBJHASH, M_WAITOK); 987 entry->object = object; 988 989 vm_object_cache_lock(); 990 TAILQ_INSERT_TAIL(bucket, entry, hash_links); 991 vm_object_cache_unlock(); 992 } 993 994 /* 995 * vm_object_remove: 996 * 997 * Remove the pager from the hash table. 998 * Note: This assumes that the object cache 999 * is locked. XXX this should be fixed 1000 * by reorganizing vm_object_deallocate. 1001 */ 1002 void 1003 vm_object_remove(pager) 1004 register vm_pager_t pager; 1005 { 1006 struct vm_object_hash_head *bucket; 1007 register vm_object_hash_entry_t entry; 1008 register vm_object_t object; 1009 1010 bucket = &vm_object_hashtable[vm_object_hash(pager)]; 1011 1012 for (entry = bucket->tqh_first; 1013 entry != NULL; 1014 entry = entry->hash_links.tqe_next) { 1015 object = entry->object; 1016 if (object->pager == pager) { 1017 TAILQ_REMOVE(bucket, entry, hash_links); 1018 free((caddr_t) entry, M_VMOBJHASH); 1019 break; 1020 } 1021 } 1022 } 1023 1024 /* 1025 * this version of collapse allows the operation to occur earlier and 1026 * when paging_in_progress is true for an object... This is not a complete 1027 * operation, but should plug 99.9% of the rest of the leaks. 1028 */ 1029 static void 1030 vm_object_qcollapse(object) 1031 register vm_object_t object; 1032 { 1033 register vm_object_t backing_object; 1034 register vm_offset_t backing_offset, new_offset; 1035 register vm_page_t p, pp; 1036 register vm_size_t size; 1037 1038 backing_object = object->shadow; 1039 if (!backing_object) 1040 return; 1041 if ((backing_object->flags & OBJ_INTERNAL) == 0) 1042 return; 1043 if (backing_object->shadow != NULL && 1044 backing_object->shadow->copy == backing_object) 1045 return; 1046 if (backing_object->ref_count != 1) 1047 return; 1048 1049 backing_object->ref_count += 2; 1050 1051 backing_offset = object->shadow_offset; 1052 size = object->size; 1053 p = backing_object->memq.tqh_first; 1054 while (p) { 1055 vm_page_t next; 1056 1057 next = p->listq.tqe_next; 1058 if ((p->flags & (PG_BUSY | PG_FICTITIOUS | PG_CACHE)) || 1059 !p->valid || p->hold_count || p->wire_count || p->busy || p->bmapped) { 1060 p = next; 1061 continue; 1062 } 1063 pmap_page_protect(VM_PAGE_TO_PHYS(p), VM_PROT_NONE); 1064 new_offset = (p->offset - backing_offset); 1065 if (p->offset < backing_offset || 1066 new_offset >= size) { 1067 if (backing_object->pager) 1068 swap_pager_freespace(backing_object->pager, 1069 backing_object->paging_offset + p->offset, PAGE_SIZE); 1070 vm_page_lock_queues(); 1071 vm_page_free(p); 1072 vm_page_unlock_queues(); 1073 } else { 1074 pp = vm_page_lookup(object, new_offset); 1075 if (pp != NULL || (object->pager && vm_pager_has_page(object->pager, 1076 object->paging_offset + new_offset))) { 1077 if (backing_object->pager) 1078 swap_pager_freespace(backing_object->pager, 1079 backing_object->paging_offset + p->offset, PAGE_SIZE); 1080 vm_page_lock_queues(); 1081 vm_page_free(p); 1082 vm_page_unlock_queues(); 1083 } else { 1084 if( backing_object->pager) 1085 swap_pager_freespace(backing_object->pager, 1086 backing_object->paging_offset + p->offset, PAGE_SIZE); 1087 vm_page_rename(p, object, new_offset); 1088 p->dirty = VM_PAGE_BITS_ALL; 1089 } 1090 } 1091 p = next; 1092 } 1093 backing_object->ref_count -= 2; 1094 } 1095 1096 boolean_t vm_object_collapse_allowed = TRUE; 1097 1098 /* 1099 * vm_object_collapse: 1100 * 1101 * Collapse an object with the object backing it. 1102 * Pages in the backing object are moved into the 1103 * parent, and the backing object is deallocated. 1104 * 1105 * Requires that the object be locked and the page 1106 * queues be unlocked. 1107 * 1108 * This routine has significant changes by John S. Dyson 1109 * to fix some swap memory leaks. 18 Dec 93 1110 * 1111 */ 1112 void 1113 vm_object_collapse(object) 1114 register vm_object_t object; 1115 1116 { 1117 register vm_object_t backing_object; 1118 register vm_offset_t backing_offset; 1119 register vm_size_t size; 1120 register vm_offset_t new_offset; 1121 register vm_page_t p, pp; 1122 1123 if (!vm_object_collapse_allowed) 1124 return; 1125 1126 while (TRUE) { 1127 /* 1128 * Verify that the conditions are right for collapse: 1129 * 1130 * The object exists and no pages in it are currently being paged 1131 * out. 1132 */ 1133 if (object == NULL) 1134 return; 1135 1136 /* 1137 * Make sure there is a backing object. 1138 */ 1139 if ((backing_object = object->shadow) == NULL) 1140 return; 1141 1142 if ((object->flags & OBJ_DEAD) || (backing_object->flags & OBJ_DEAD)) 1143 return; 1144 1145 if (object->paging_in_progress != 0) { 1146 if (backing_object) { 1147 if (vm_object_lock_try(backing_object)) { 1148 vm_object_qcollapse(object); 1149 vm_object_unlock(backing_object); 1150 } 1151 } 1152 return; 1153 } 1154 1155 vm_object_lock(backing_object); 1156 /* 1157 * ... The backing object is not read_only, and no pages in 1158 * the backing object are currently being paged out. The 1159 * backing object is internal. 1160 */ 1161 1162 if ((backing_object->flags & OBJ_INTERNAL) == 0 || 1163 backing_object->paging_in_progress != 0) { 1164 vm_object_qcollapse(object); 1165 vm_object_unlock(backing_object); 1166 return; 1167 } 1168 /* 1169 * The backing object can't be a copy-object: the 1170 * shadow_offset for the copy-object must stay as 0. 1171 * Furthermore (for the 'we have all the pages' case), if we 1172 * bypass backing_object and just shadow the next object in 1173 * the chain, old pages from that object would then have to be 1174 * copied BOTH into the (former) backing_object and into the 1175 * parent object. 1176 */ 1177 if (backing_object->shadow != NULL && 1178 backing_object->shadow->copy == backing_object) { 1179 vm_object_unlock(backing_object); 1180 return; 1181 } 1182 /* 1183 * we can deal only with the swap pager 1184 */ 1185 if ((object->pager && 1186 object->pager->pg_type != PG_SWAP) || 1187 (backing_object->pager && 1188 backing_object->pager->pg_type != PG_SWAP)) { 1189 vm_object_unlock(backing_object); 1190 return; 1191 } 1192 /* 1193 * We know that we can either collapse the backing object (if 1194 * the parent is the only reference to it) or (perhaps) remove 1195 * the parent's reference to it. 1196 */ 1197 1198 backing_offset = object->shadow_offset; 1199 size = object->size; 1200 1201 /* 1202 * If there is exactly one reference to the backing object, we 1203 * can collapse it into the parent. 1204 */ 1205 1206 if (backing_object->ref_count == 1) { 1207 1208 backing_object->flags |= OBJ_DEAD; 1209 /* 1210 * We can collapse the backing object. 1211 * 1212 * Move all in-memory pages from backing_object to the 1213 * parent. Pages that have been paged out will be 1214 * overwritten by any of the parent's pages that 1215 * shadow them. 1216 */ 1217 1218 while ((p = backing_object->memq.tqh_first) != 0) { 1219 1220 new_offset = (p->offset - backing_offset); 1221 1222 /* 1223 * If the parent has a page here, or if this 1224 * page falls outside the parent, dispose of 1225 * it. 1226 * 1227 * Otherwise, move it as planned. 1228 */ 1229 1230 if (p->offset < backing_offset || 1231 new_offset >= size) { 1232 vm_page_lock_queues(); 1233 pmap_page_protect(VM_PAGE_TO_PHYS(p), VM_PROT_NONE); 1234 PAGE_WAKEUP(p); 1235 vm_page_free(p); 1236 vm_page_unlock_queues(); 1237 } else { 1238 pp = vm_page_lookup(object, new_offset); 1239 if (pp != NULL || (object->pager && vm_pager_has_page(object->pager, 1240 object->paging_offset + new_offset))) { 1241 vm_page_lock_queues(); 1242 pmap_page_protect(VM_PAGE_TO_PHYS(p), VM_PROT_NONE); 1243 PAGE_WAKEUP(p); 1244 vm_page_free(p); 1245 vm_page_unlock_queues(); 1246 } else { 1247 vm_page_rename(p, object, new_offset); 1248 } 1249 } 1250 } 1251 1252 /* 1253 * Move the pager from backing_object to object. 1254 */ 1255 1256 if (backing_object->pager) { 1257 backing_object->paging_in_progress++; 1258 if (object->pager) { 1259 vm_pager_t bopager; 1260 1261 object->paging_in_progress++; 1262 /* 1263 * copy shadow object pages into ours 1264 * and destroy unneeded pages in 1265 * shadow object. 1266 */ 1267 bopager = backing_object->pager; 1268 vm_object_remove(backing_object->pager); 1269 backing_object->pager = NULL; 1270 swap_pager_copy( 1271 bopager, backing_object->paging_offset, 1272 object->pager, object->paging_offset, 1273 object->shadow_offset); 1274 object->paging_in_progress--; 1275 if (object->paging_in_progress == 0 && 1276 (object->flags & OBJ_PIPWNT)) { 1277 object->flags &= ~OBJ_PIPWNT; 1278 wakeup((caddr_t) object); 1279 } 1280 } else { 1281 object->paging_in_progress++; 1282 /* 1283 * grab the shadow objects pager 1284 */ 1285 object->pager = backing_object->pager; 1286 object->paging_offset = backing_object->paging_offset + backing_offset; 1287 vm_object_remove(backing_object->pager); 1288 backing_object->pager = NULL; 1289 /* 1290 * free unnecessary blocks 1291 */ 1292 swap_pager_freespace(object->pager, 0, object->paging_offset); 1293 object->paging_in_progress--; 1294 if (object->paging_in_progress == 0 && 1295 (object->flags & OBJ_PIPWNT)) { 1296 object->flags &= ~OBJ_PIPWNT; 1297 wakeup((caddr_t) object); 1298 } 1299 } 1300 1301 backing_object->paging_in_progress--; 1302 if (backing_object->paging_in_progress == 0 && 1303 (backing_object->flags & OBJ_PIPWNT)) { 1304 backing_object->flags &= ~OBJ_PIPWNT; 1305 wakeup((caddr_t) backing_object); 1306 } 1307 } 1308 /* 1309 * Object now shadows whatever backing_object did. 1310 * Note that the reference to backing_object->shadow 1311 * moves from within backing_object to within object. 1312 */ 1313 1314 TAILQ_REMOVE(&object->shadow->reverse_shadow_head, object, 1315 reverse_shadow_list); 1316 if (backing_object->shadow) 1317 TAILQ_REMOVE(&backing_object->shadow->reverse_shadow_head, 1318 backing_object, reverse_shadow_list); 1319 object->shadow = backing_object->shadow; 1320 if (object->shadow) 1321 TAILQ_INSERT_TAIL(&object->shadow->reverse_shadow_head, 1322 object, reverse_shadow_list); 1323 1324 object->shadow_offset += backing_object->shadow_offset; 1325 /* 1326 * Discard backing_object. 1327 * 1328 * Since the backing object has no pages, no pager left, 1329 * and no object references within it, all that is 1330 * necessary is to dispose of it. 1331 */ 1332 1333 vm_object_unlock(backing_object); 1334 1335 simple_lock(&vm_object_list_lock); 1336 TAILQ_REMOVE(&vm_object_list, backing_object, 1337 object_list); 1338 vm_object_count--; 1339 simple_unlock(&vm_object_list_lock); 1340 1341 free((caddr_t) backing_object, M_VMOBJ); 1342 1343 object_collapses++; 1344 } else { 1345 /* 1346 * If all of the pages in the backing object are 1347 * shadowed by the parent object, the parent object no 1348 * longer has to shadow the backing object; it can 1349 * shadow the next one in the chain. 1350 * 1351 * The backing object must not be paged out - we'd have 1352 * to check all of the paged-out pages, as well. 1353 */ 1354 1355 if (backing_object->pager != NULL) { 1356 vm_object_unlock(backing_object); 1357 return; 1358 } 1359 /* 1360 * Should have a check for a 'small' number of pages 1361 * here. 1362 */ 1363 1364 for (p = backing_object->memq.tqh_first; p; p = p->listq.tqe_next) { 1365 new_offset = (p->offset - backing_offset); 1366 1367 /* 1368 * If the parent has a page here, or if this 1369 * page falls outside the parent, keep going. 1370 * 1371 * Otherwise, the backing_object must be left in 1372 * the chain. 1373 */ 1374 1375 if (p->offset >= backing_offset && 1376 new_offset <= size && 1377 ((pp = vm_page_lookup(object, new_offset)) == NULL || 1378 !pp->valid) && 1379 (!object->pager || !vm_pager_has_page(object->pager, object->paging_offset + new_offset))) { 1380 /* 1381 * Page still needed. Can't go any 1382 * further. 1383 */ 1384 vm_object_unlock(backing_object); 1385 return; 1386 } 1387 } 1388 1389 /* 1390 * Make the parent shadow the next object in the 1391 * chain. Deallocating backing_object will not remove 1392 * it, since its reference count is at least 2. 1393 */ 1394 1395 TAILQ_REMOVE(&object->shadow->reverse_shadow_head, 1396 object, reverse_shadow_list); 1397 vm_object_reference(object->shadow = backing_object->shadow); 1398 if (object->shadow) 1399 TAILQ_INSERT_TAIL(&object->shadow->reverse_shadow_head, 1400 object, reverse_shadow_list); 1401 object->shadow_offset += backing_object->shadow_offset; 1402 1403 /* 1404 * Backing object might have had a copy pointer to us. 1405 * If it did, clear it. 1406 */ 1407 if (backing_object->copy == object) { 1408 backing_object->copy = NULL; 1409 } 1410 /* 1411 * Drop the reference count on backing_object. Since 1412 * its ref_count was at least 2, it will not vanish; 1413 * so we don't need to call vm_object_deallocate. 1414 */ 1415 if (backing_object->ref_count == 1) 1416 printf("should have called obj deallocate\n"); 1417 backing_object->ref_count--; 1418 vm_object_unlock(backing_object); 1419 1420 object_bypasses++; 1421 1422 } 1423 1424 /* 1425 * Try again with this object's new backing object. 1426 */ 1427 } 1428 } 1429 1430 /* 1431 * vm_object_page_remove: [internal] 1432 * 1433 * Removes all physical pages in the specified 1434 * object range from the object's list of pages. 1435 * 1436 * The object must be locked. 1437 */ 1438 void 1439 vm_object_page_remove(object, start, end) 1440 register vm_object_t object; 1441 register vm_offset_t start; 1442 register vm_offset_t end; 1443 { 1444 register vm_page_t p, next; 1445 vm_offset_t size; 1446 int s; 1447 1448 if (object == NULL) 1449 return; 1450 1451 object->paging_in_progress++; 1452 start = trunc_page(start); 1453 end = round_page(end); 1454 again: 1455 size = end - start; 1456 if (size > 4 * PAGE_SIZE || size >= object->size / 4) { 1457 for (p = object->memq.tqh_first; p != NULL; p = next) { 1458 next = p->listq.tqe_next; 1459 if ((start <= p->offset) && (p->offset < end)) { 1460 s = splhigh(); 1461 if (p->bmapped) { 1462 splx(s); 1463 continue; 1464 } 1465 if ((p->flags & PG_BUSY) || p->busy) { 1466 p->flags |= PG_WANTED; 1467 tsleep((caddr_t) p, PVM, "vmopar", 0); 1468 splx(s); 1469 goto again; 1470 } 1471 splx(s); 1472 pmap_page_protect(VM_PAGE_TO_PHYS(p), VM_PROT_NONE); 1473 vm_page_lock_queues(); 1474 PAGE_WAKEUP(p); 1475 vm_page_free(p); 1476 vm_page_unlock_queues(); 1477 } 1478 } 1479 } else { 1480 while (size > 0) { 1481 while ((p = vm_page_lookup(object, start)) != 0) { 1482 s = splhigh(); 1483 if (p->bmapped) { 1484 splx(s); 1485 break; 1486 } 1487 if ((p->flags & PG_BUSY) || p->busy) { 1488 p->flags |= PG_WANTED; 1489 tsleep((caddr_t) p, PVM, "vmopar", 0); 1490 splx(s); 1491 goto again; 1492 } 1493 splx(s); 1494 pmap_page_protect(VM_PAGE_TO_PHYS(p), VM_PROT_NONE); 1495 vm_page_lock_queues(); 1496 PAGE_WAKEUP(p); 1497 vm_page_free(p); 1498 vm_page_unlock_queues(); 1499 } 1500 start += PAGE_SIZE; 1501 size -= PAGE_SIZE; 1502 } 1503 } 1504 --object->paging_in_progress; 1505 if (object->paging_in_progress == 0 && (object->flags & OBJ_PIPWNT)) { 1506 object->flags &= ~OBJ_PIPWNT; 1507 wakeup((caddr_t) object); 1508 } 1509 } 1510 1511 /* 1512 * Routine: vm_object_coalesce 1513 * Function: Coalesces two objects backing up adjoining 1514 * regions of memory into a single object. 1515 * 1516 * returns TRUE if objects were combined. 1517 * 1518 * NOTE: Only works at the moment if the second object is NULL - 1519 * if it's not, which object do we lock first? 1520 * 1521 * Parameters: 1522 * prev_object First object to coalesce 1523 * prev_offset Offset into prev_object 1524 * next_object Second object into coalesce 1525 * next_offset Offset into next_object 1526 * 1527 * prev_size Size of reference to prev_object 1528 * next_size Size of reference to next_object 1529 * 1530 * Conditions: 1531 * The object must *not* be locked. 1532 */ 1533 boolean_t 1534 vm_object_coalesce(prev_object, next_object, 1535 prev_offset, next_offset, 1536 prev_size, next_size) 1537 register vm_object_t prev_object; 1538 vm_object_t next_object; 1539 vm_offset_t prev_offset, next_offset; 1540 vm_size_t prev_size, next_size; 1541 { 1542 vm_size_t newsize; 1543 1544 if (next_object != NULL) { 1545 return (FALSE); 1546 } 1547 if (prev_object == NULL) { 1548 return (TRUE); 1549 } 1550 vm_object_lock(prev_object); 1551 1552 /* 1553 * Try to collapse the object first 1554 */ 1555 vm_object_collapse(prev_object); 1556 1557 /* 1558 * Can't coalesce if: . more than one reference . paged out . shadows 1559 * another object . has a copy elsewhere (any of which mean that the 1560 * pages not mapped to prev_entry may be in use anyway) 1561 */ 1562 1563 if (prev_object->ref_count > 1 || 1564 prev_object->pager != NULL || 1565 prev_object->shadow != NULL || 1566 prev_object->copy != NULL) { 1567 vm_object_unlock(prev_object); 1568 return (FALSE); 1569 } 1570 /* 1571 * Remove any pages that may still be in the object from a previous 1572 * deallocation. 1573 */ 1574 1575 vm_object_page_remove(prev_object, 1576 prev_offset + prev_size, 1577 prev_offset + prev_size + next_size); 1578 1579 /* 1580 * Extend the object if necessary. 1581 */ 1582 newsize = prev_offset + prev_size + next_size; 1583 if (newsize > prev_object->size) 1584 prev_object->size = newsize; 1585 1586 vm_object_unlock(prev_object); 1587 return (TRUE); 1588 } 1589 1590 /* 1591 * returns page after looking up in shadow chain 1592 */ 1593 1594 vm_page_t 1595 vm_object_page_lookup(object, offset) 1596 vm_object_t object; 1597 vm_offset_t offset; 1598 { 1599 vm_page_t m; 1600 1601 if (!(m = vm_page_lookup(object, offset))) { 1602 if (!object->shadow) 1603 return 0; 1604 else 1605 return vm_object_page_lookup(object->shadow, offset + object->shadow_offset); 1606 } 1607 return m; 1608 } 1609 1610 int 1611 _vm_object_in_map(map, object, entry) 1612 vm_map_t map; 1613 vm_object_t object; 1614 vm_map_entry_t entry; 1615 { 1616 vm_map_t tmpm; 1617 vm_map_entry_t tmpe; 1618 vm_object_t obj; 1619 int entcount; 1620 1621 if (map == 0) 1622 return 0; 1623 1624 if (entry == 0) { 1625 tmpe = map->header.next; 1626 entcount = map->nentries; 1627 while (entcount-- && (tmpe != &map->header)) { 1628 if( _vm_object_in_map(map, object, tmpe)) { 1629 return 1; 1630 } 1631 tmpe = tmpe->next; 1632 } 1633 } else if (entry->is_sub_map || entry->is_a_map) { 1634 tmpm = entry->object.share_map; 1635 tmpe = tmpm->header.next; 1636 entcount = tmpm->nentries; 1637 while (entcount-- && tmpe != &tmpm->header) { 1638 if( _vm_object_in_map(tmpm, object, tmpe)) { 1639 return 1; 1640 } 1641 tmpe = tmpe->next; 1642 } 1643 } else if (obj = entry->object.vm_object) { 1644 for(; obj; obj=obj->shadow) 1645 if( obj == object) { 1646 return 1; 1647 } 1648 } 1649 return 0; 1650 } 1651 1652 int 1653 vm_object_in_map( object) 1654 vm_object_t object; 1655 { 1656 struct proc *p; 1657 for (p = (struct proc *) allproc; p != NULL; p = p->p_next) { 1658 if( !p->p_vmspace /* || (p->p_flag & (P_SYSTEM|P_WEXIT)) */) 1659 continue; 1660 /* 1661 if (p->p_stat != SRUN && p->p_stat != SSLEEP) { 1662 continue; 1663 } 1664 */ 1665 if( _vm_object_in_map(&p->p_vmspace->vm_map, object, 0)) 1666 return 1; 1667 } 1668 if( _vm_object_in_map( kernel_map, object, 0)) 1669 return 1; 1670 if( _vm_object_in_map( kmem_map, object, 0)) 1671 return 1; 1672 if( _vm_object_in_map( pager_map, object, 0)) 1673 return 1; 1674 if( _vm_object_in_map( buffer_map, object, 0)) 1675 return 1; 1676 if( _vm_object_in_map( io_map, object, 0)) 1677 return 1; 1678 if( _vm_object_in_map( phys_map, object, 0)) 1679 return 1; 1680 if( _vm_object_in_map( mb_map, object, 0)) 1681 return 1; 1682 if( _vm_object_in_map( u_map, object, 0)) 1683 return 1; 1684 return 0; 1685 } 1686 1687 void 1688 vm_object_check() { 1689 int i; 1690 int maxhash = 0; 1691 vm_object_t object; 1692 vm_object_hash_entry_t entry; 1693 1694 /* 1695 * make sure that no internal objs are hashed 1696 */ 1697 for (i=0; i<VM_OBJECT_HASH_COUNT;i++) { 1698 int lsize = 0; 1699 for (entry = vm_object_hashtable[i].tqh_first; 1700 entry != NULL; 1701 entry = entry->hash_links.tqe_next) { 1702 if( entry->object->flags & OBJ_INTERNAL) { 1703 printf("vmochk: internal obj on hash: size: %d\n", entry->object->size); 1704 } 1705 ++lsize; 1706 } 1707 if( lsize > maxhash) 1708 maxhash = lsize; 1709 } 1710 1711 printf("maximum object hash queue size: %d\n", maxhash); 1712 1713 /* 1714 * make sure that internal objs are in a map somewhere 1715 * and none have zero ref counts. 1716 */ 1717 for (object = vm_object_list.tqh_first; 1718 object != NULL; 1719 object = object->object_list.tqe_next) { 1720 if( object->flags & OBJ_INTERNAL) { 1721 if( object->ref_count == 0) { 1722 printf("vmochk: internal obj has zero ref count: %d\n", 1723 object->size); 1724 } 1725 if( !vm_object_in_map(object)) { 1726 printf("vmochk: internal obj is not in a map: ref: %d, size: %d, pager: 0x%x, shadow: 0x%x\n", object->ref_count, object->size, object->pager, object->shadow); 1727 } 1728 } 1729 } 1730 } 1731 1732 #define DEBUG 1733 #if defined(DEBUG) || defined(DDB) 1734 /* 1735 * vm_object_print: [ debug ] 1736 */ 1737 void 1738 vm_object_print(object, full) 1739 vm_object_t object; 1740 boolean_t full; 1741 { 1742 register vm_page_t p; 1743 extern indent; 1744 1745 register int count; 1746 1747 if (object == NULL) 1748 return; 1749 1750 iprintf("Object 0x%x: size=0x%x, res=%d, ref=%d, ", 1751 (int) object, (int) object->size, 1752 object->resident_page_count, object->ref_count); 1753 printf("pager=0x%x+0x%x, shadow=(0x%x)+0x%x\n", 1754 (int) object->pager, (int) object->paging_offset, 1755 (int) object->shadow, (int) object->shadow_offset); 1756 printf("cache: next=%p, prev=%p\n", 1757 object->cached_list.tqe_next, object->cached_list.tqe_prev); 1758 1759 if (!full) 1760 return; 1761 1762 indent += 2; 1763 count = 0; 1764 for (p = object->memq.tqh_first; p != NULL; p = p->listq.tqe_next) { 1765 if (count == 0) 1766 iprintf("memory:="); 1767 else if (count == 6) { 1768 printf("\n"); 1769 iprintf(" ..."); 1770 count = 0; 1771 } else 1772 printf(","); 1773 count++; 1774 1775 printf("(off=0x%lx,page=0x%lx)", 1776 (u_long) p->offset, (u_long) VM_PAGE_TO_PHYS(p)); 1777 } 1778 if (count != 0) 1779 printf("\n"); 1780 indent -= 2; 1781 } 1782 #endif /* defined(DEBUG) || defined(DDB) */ 1783