Comment out porogrammer-readable fd name set,
[unix-history] / sys / vm / vm_object.c
CommitLineData
15637ed4
RG
1/*
2 * Copyright (c) 1991 Regents of the University of California.
3 * 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 *
1284e777 36 * from: @(#)vm_object.c 7.4 (Berkeley) 5/7/91
fde1aeb2 37 * $Id: vm_object.c,v 1.10 1993/11/25 12:07:41 davidg Exp $
1284e777
RG
38 */
39
40/*
15637ed4
RG
41 * Copyright (c) 1987, 1990 Carnegie-Mellon University.
42 * All rights reserved.
43 *
44 * Authors: Avadis Tevanian, Jr., Michael Wayne Young
45 *
46 * Permission to use, copy, modify and distribute this software and
47 * its documentation is hereby granted, provided that both the copyright
48 * notice and this permission notice appear in all copies of the
49 * software, derivative works or modified versions, and any portions
50 * thereof, and that both notices appear in supporting documentation.
51 *
52 * CARNEGIE MELLON ALLOWS FREE USE OF THIS SOFTWARE IN ITS "AS IS"
53 * CONDITION. CARNEGIE MELLON DISCLAIMS ANY LIABILITY OF ANY KIND
54 * FOR ANY DAMAGES WHATSOEVER RESULTING FROM THE USE OF THIS SOFTWARE.
55 *
56 * Carnegie Mellon requests users of this software to return to
57 *
58 * Software Distribution Coordinator or Software.Distribution@CS.CMU.EDU
59 * School of Computer Science
60 * Carnegie Mellon University
61 * Pittsburgh PA 15213-3890
62 *
63 * any improvements or extensions that they make and grant Carnegie the
64 * rights to redistribute these changes.
15637ed4
RG
65 */
66
67/*
68 * Virtual memory object module.
69 */
70
71#include "param.h"
fde1aeb2 72#include "systm.h"
15637ed4
RG
73#include "malloc.h"
74
75#include "vm.h"
76#include "vm_page.h"
fde1aeb2
GW
77#include "ddb.h"
78
15637ed4 79
4c45483e
GW
80static void _vm_object_allocate(vm_size_t, vm_object_t);
81static void vm_object_deactivate_pages(vm_object_t);
82static void vm_object_cache_trim(void);
83static void vm_object_remove(vm_pager_t);
84
15637ed4
RG
85/*
86 * Virtual memory objects maintain the actual data
87 * associated with allocated virtual memory. A given
88 * page of memory exists within exactly one object.
89 *
90 * An object is only deallocated when all "references"
91 * are given up. Only one "reference" to a given
92 * region of an object should be writeable.
93 *
94 * Associated with each object is a list of all resident
95 * memory pages belonging to that object; this list is
96 * maintained by the "vm_page" module, and locked by the object's
97 * lock.
98 *
99 * Each object also records a "pager" routine which is
100 * used to retrieve (and store) pages to the proper backing
101 * storage. In addition, objects may be backed by other
102 * objects from which they were virtual-copied.
103 *
104 * The only items within the object structure which are
105 * modified after time of creation are:
106 * reference count locked by object's lock
107 * pager routine locked by object's lock
108 *
109 */
110
bbc3f849
GW
111queue_head_t vm_object_cached_list; /* list of objects persisting */
112int vm_object_cached; /* size of cached list */
113simple_lock_data_t vm_cache_lock; /* lock for object cache */
114
115queue_head_t vm_object_list; /* list of allocated objects */
116long vm_object_count; /* count of all objects */
117simple_lock_data_t vm_object_list_lock;
118 /* lock for object list and count */
119
120vm_object_t kernel_object; /* the single kernel object */
121vm_object_t kmem_object;
122
15637ed4
RG
123struct vm_object kernel_object_store;
124struct vm_object kmem_object_store;
125
126#define VM_OBJECT_HASH_COUNT 157
127
128int vm_cache_max = 100; /* can patch if necessary */
129queue_head_t vm_object_hashtable[VM_OBJECT_HASH_COUNT];
130
131long object_collapses = 0;
132long object_bypasses = 0;
133
134/*
135 * vm_object_init:
136 *
137 * Initialize the VM objects module.
138 */
139void vm_object_init()
140{
141 register int i;
142
143 queue_init(&vm_object_cached_list);
144 queue_init(&vm_object_list);
145 vm_object_count = 0;
146 simple_lock_init(&vm_cache_lock);
147 simple_lock_init(&vm_object_list_lock);
148
149 for (i = 0; i < VM_OBJECT_HASH_COUNT; i++)
150 queue_init(&vm_object_hashtable[i]);
151
152 kernel_object = &kernel_object_store;
153 _vm_object_allocate(VM_MAX_KERNEL_ADDRESS - VM_MIN_KERNEL_ADDRESS,
154 kernel_object);
155
156 kmem_object = &kmem_object_store;
157 _vm_object_allocate(VM_KMEM_SIZE + VM_MBUF_SIZE, kmem_object);
158}
159
160/*
161 * vm_object_allocate:
162 *
163 * Returns a new object with the given size.
164 */
165
166vm_object_t vm_object_allocate(size)
167 vm_size_t size;
168{
169 register vm_object_t result;
170
171 result = (vm_object_t)
172 malloc((u_long)sizeof *result, M_VMOBJ, M_WAITOK);
173
174 _vm_object_allocate(size, result);
175
176 return(result);
177}
178
4c45483e 179static void
15637ed4
RG
180_vm_object_allocate(size, object)
181 vm_size_t size;
182 register vm_object_t object;
183{
184 queue_init(&object->memq);
185 vm_object_lock_init(object);
186 object->ref_count = 1;
187 object->resident_page_count = 0;
188 object->size = size;
189 object->can_persist = FALSE;
190 object->paging_in_progress = 0;
191 object->copy = NULL;
192
193 /*
194 * Object starts out read-write, with no pager.
195 */
196
197 object->pager = NULL;
198 object->pager_ready = FALSE;
199 object->internal = TRUE; /* vm_allocate_with_pager will reset */
200 object->paging_offset = 0;
201 object->shadow = NULL;
202 object->shadow_offset = (vm_offset_t) 0;
203
204 simple_lock(&vm_object_list_lock);
205 queue_enter(&vm_object_list, object, vm_object_t, object_list);
206 vm_object_count++;
207 simple_unlock(&vm_object_list_lock);
208}
209
210/*
211 * vm_object_reference:
212 *
213 * Gets another reference to the given object.
214 */
215void vm_object_reference(object)
216 register vm_object_t object;
217{
218 if (object == NULL)
219 return;
220
221 vm_object_lock(object);
222 object->ref_count++;
223 vm_object_unlock(object);
224}
225
226/*
227 * vm_object_deallocate:
228 *
229 * Release a reference to the specified object,
230 * gained either through a vm_object_allocate
231 * or a vm_object_reference call. When all references
232 * are gone, storage associated with this object
233 * may be relinquished.
234 *
235 * No object may be locked.
236 */
237void vm_object_deallocate(object)
238 register vm_object_t object;
239{
240 vm_object_t temp;
241
242 while (object != NULL) {
243
244 /*
245 * The cache holds a reference (uncounted) to
246 * the object; we must lock it before removing
247 * the object.
248 */
249
250 vm_object_cache_lock();
251
252 /*
253 * Lose the reference
254 */
255 vm_object_lock(object);
256 if (--(object->ref_count) != 0) {
257
258 /*
259 * If there are still references, then
260 * we are done.
261 */
262 vm_object_unlock(object);
263 vm_object_cache_unlock();
264 return;
265 }
266
267 /*
268 * See if this object can persist. If so, enter
269 * it in the cache, then deactivate all of its
270 * pages.
271 */
272
273 if (object->can_persist) {
3ad802c6 274#ifdef DIAGNOSTIC
15637ed4
RG
275 register vm_page_t p;
276
277 /*
278 * Check for dirty pages in object
279 * Print warning as this may signify kernel bugs
280 * pk@cs.few.eur.nl - 4/15/93
281 */
282 p = (vm_page_t) queue_first(&object->memq);
283 while (!queue_end(&object->memq, (queue_entry_t) p)) {
284 VM_PAGE_CHECK(p);
285
286 if (pmap_is_modified(VM_PAGE_TO_PHYS(p)) ||
287 !p->clean) {
288
289 printf("vm_object_dealloc: persistent object %x isn't clean\n", object);
290 goto cant_persist;
291 }
292
293 p = (vm_page_t) queue_next(&p->listq);
294 }
3ad802c6 295#endif /* DIAGNOSTIC */
15637ed4
RG
296
297 queue_enter(&vm_object_cached_list, object,
298 vm_object_t, cached_list);
299 vm_object_cached++;
300 vm_object_cache_unlock();
301
302 vm_object_deactivate_pages(object);
303 vm_object_unlock(object);
304
305 vm_object_cache_trim();
306 return;
307 }
308 cant_persist:;
309
310 /*
311 * Make sure no one can look us up now.
312 */
313 vm_object_remove(object->pager);
314 vm_object_cache_unlock();
315
316 temp = object->shadow;
317 vm_object_terminate(object);
318 /* unlocks and deallocates object */
319 object = temp;
320 }
321}
322
323
324/*
325 * vm_object_terminate actually destroys the specified object, freeing
326 * up all previously used resources.
327 *
328 * The object must be locked.
329 */
330void vm_object_terminate(object)
331 register vm_object_t object;
332{
333 register vm_page_t p;
334 vm_object_t shadow_object;
335
336 /*
337 * Detach the object from its shadow if we are the shadow's
338 * copy.
339 */
340 if ((shadow_object = object->shadow) != NULL) {
341 vm_object_lock(shadow_object);
342 if (shadow_object->copy == object)
343 shadow_object->copy = NULL;
344#if 0
345 else if (shadow_object->copy != NULL)
346 panic("vm_object_terminate: copy/shadow inconsistency");
347#endif
348 vm_object_unlock(shadow_object);
349 }
350
351 /*
352 * Wait until the pageout daemon is through
353 * with the object.
354 */
355
356 while (object->paging_in_progress != 0) {
4c45483e 357 vm_object_sleep((int)object, object, FALSE);
15637ed4
RG
358 vm_object_lock(object);
359 }
360
361
362 /*
363 * While the paging system is locked,
364 * pull the object's pages off the active
365 * and inactive queues. This keeps the
366 * pageout daemon from playing with them
367 * during vm_pager_deallocate.
368 *
369 * We can't free the pages yet, because the
370 * object's pager may have to write them out
371 * before deallocating the paging space.
372 */
373
374 p = (vm_page_t) queue_first(&object->memq);
375 while (!queue_end(&object->memq, (queue_entry_t) p)) {
376 VM_PAGE_CHECK(p);
377
378 vm_page_lock_queues();
379 if (p->active) {
380 queue_remove(&vm_page_queue_active, p, vm_page_t,
381 pageq);
382 p->active = FALSE;
383 vm_page_active_count--;
384 }
385
386 if (p->inactive) {
387 queue_remove(&vm_page_queue_inactive, p, vm_page_t,
388 pageq);
389 p->inactive = FALSE;
390 vm_page_inactive_count--;
391 }
392 vm_page_unlock_queues();
393 p = (vm_page_t) queue_next(&p->listq);
394 }
395
396 vm_object_unlock(object);
397
398 if (object->paging_in_progress != 0)
399 panic("vm_object_deallocate: pageout in progress");
400
401 /*
402 * Clean and free the pages, as appropriate.
403 * All references to the object are gone,
404 * so we don't need to lock it.
405 */
406
407 if (!object->internal) {
408 vm_object_lock(object);
409 vm_object_page_clean(object, 0, 0);
410 vm_object_unlock(object);
411 }
412 while (!queue_empty(&object->memq)) {
413 p = (vm_page_t) queue_first(&object->memq);
414
415 VM_PAGE_CHECK(p);
416
417 vm_page_lock_queues();
418 vm_page_free(p);
419 vm_page_unlock_queues();
420 }
421
422 /*
423 * Let the pager know object is dead.
424 */
425
426 if (object->pager != NULL)
427 vm_pager_deallocate(object->pager);
428
429
430 simple_lock(&vm_object_list_lock);
431 queue_remove(&vm_object_list, object, vm_object_t, object_list);
432 vm_object_count--;
433 simple_unlock(&vm_object_list_lock);
434
435 /*
436 * Free the space for the object.
437 */
438
439 free((caddr_t)object, M_VMOBJ);
440}
441
442/*
443 * vm_object_page_clean
444 *
445 * Clean all dirty pages in the specified range of object.
446 * Leaves page on whatever queue it is currently on.
447 *
448 * Odd semantics: if start == end, we clean everything.
449 *
450 * The object must be locked.
451 */
4c45483e 452void
15637ed4
RG
453vm_object_page_clean(object, start, end)
454 register vm_object_t object;
455 register vm_offset_t start;
456 register vm_offset_t end;
457{
458 register vm_page_t p;
459
460 if (object->pager == NULL)
461 return;
462
463again:
464 p = (vm_page_t) queue_first(&object->memq);
465 while (!queue_end(&object->memq, (queue_entry_t) p)) {
466 if (start == end ||
467 p->offset >= start && p->offset < end) {
468 if (p->clean && pmap_is_modified(VM_PAGE_TO_PHYS(p)))
469 p->clean = FALSE;
470 pmap_page_protect(VM_PAGE_TO_PHYS(p), VM_PROT_NONE);
471 if (!p->clean) {
472 p->busy = TRUE;
473 object->paging_in_progress++;
474 vm_object_unlock(object);
475 (void) vm_pager_put(object->pager, p, TRUE);
476 vm_object_lock(object);
477 object->paging_in_progress--;
478 p->busy = FALSE;
479 PAGE_WAKEUP(p);
480 goto again;
481 }
482 }
483 p = (vm_page_t) queue_next(&p->listq);
484 }
485}
486
487/*
488 * vm_object_deactivate_pages
489 *
490 * Deactivate all pages in the specified object. (Keep its pages
491 * in memory even though it is no longer referenced.)
492 *
493 * The object must be locked.
494 */
4c45483e 495static void
15637ed4
RG
496vm_object_deactivate_pages(object)
497 register vm_object_t object;
498{
499 register vm_page_t p, next;
500
501 p = (vm_page_t) queue_first(&object->memq);
502 while (!queue_end(&object->memq, (queue_entry_t) p)) {
503 next = (vm_page_t) queue_next(&p->listq);
504 vm_page_lock_queues();
8820571b
NW
505 if (!p->busy)
506 vm_page_deactivate(p); /* optimisation from mach 3.0 -
507 * andrew@werple.apana.org.au,
508 * Feb '93
509 */
15637ed4
RG
510 vm_page_unlock_queues();
511 p = next;
512 }
513}
514
515/*
516 * Trim the object cache to size.
517 */
4c45483e 518static void
15637ed4
RG
519vm_object_cache_trim()
520{
521 register vm_object_t object;
522
523 vm_object_cache_lock();
524 while (vm_object_cached > vm_cache_max) {
525 object = (vm_object_t) queue_first(&vm_object_cached_list);
526 vm_object_cache_unlock();
527
528 if (object != vm_object_lookup(object->pager))
529 panic("vm_object_deactivate: I'm sooo confused.");
530
531 pager_cache(object, FALSE);
532
533 vm_object_cache_lock();
534 }
535 vm_object_cache_unlock();
536}
537
538
539/*
540 * vm_object_shutdown()
541 *
542 * Shut down the object system. Unfortunately, while we
543 * may be trying to do this, init is happily waiting for
544 * processes to exit, and therefore will be causing some objects
545 * to be deallocated. To handle this, we gain a fake reference
546 * to all objects we release paging areas for. This will prevent
547 * a duplicate deallocation. This routine is probably full of
548 * race conditions!
549 */
550
551void vm_object_shutdown()
552{
553 register vm_object_t object;
554
555 /*
556 * Clean up the object cache *before* we screw up the reference
557 * counts on all of the objects.
558 */
559
560 vm_object_cache_clear();
561
562 printf("free paging spaces: ");
563
564 /*
565 * First we gain a reference to each object so that
566 * no one else will deallocate them.
567 */
568
569 simple_lock(&vm_object_list_lock);
570 object = (vm_object_t) queue_first(&vm_object_list);
571 while (!queue_end(&vm_object_list, (queue_entry_t) object)) {
572 vm_object_reference(object);
573 object = (vm_object_t) queue_next(&object->object_list);
574 }
575 simple_unlock(&vm_object_list_lock);
576
577 /*
578 * Now we deallocate all the paging areas. We don't need
579 * to lock anything because we've reduced to a single
580 * processor while shutting down. This also assumes that
581 * no new objects are being created.
582 */
583
584 object = (vm_object_t) queue_first(&vm_object_list);
585 while (!queue_end(&vm_object_list, (queue_entry_t) object)) {
586 if (object->pager != NULL)
587 vm_pager_deallocate(object->pager);
588 object = (vm_object_t) queue_next(&object->object_list);
589 printf(".");
590 }
591 printf("done.\n");
592}
593
594/*
595 * vm_object_pmap_copy:
596 *
597 * Makes all physical pages in the specified
598 * object range copy-on-write. No writeable
599 * references to these pages should remain.
600 *
601 * The object must *not* be locked.
602 */
603void vm_object_pmap_copy(object, start, end)
604 register vm_object_t object;
605 register vm_offset_t start;
606 register vm_offset_t end;
607{
608 register vm_page_t p;
609
610 if (object == NULL)
611 return;
612
613 vm_object_lock(object);
614 p = (vm_page_t) queue_first(&object->memq);
615 while (!queue_end(&object->memq, (queue_entry_t) p)) {
616 if ((start <= p->offset) && (p->offset < end)) {
617 pmap_page_protect(VM_PAGE_TO_PHYS(p), VM_PROT_READ);
618 p->copy_on_write = TRUE;
619 }
620 p = (vm_page_t) queue_next(&p->listq);
621 }
622 vm_object_unlock(object);
623}
624
625/*
626 * vm_object_pmap_remove:
627 *
628 * Removes all physical pages in the specified
629 * object range from all physical maps.
630 *
631 * The object must *not* be locked.
632 */
633void vm_object_pmap_remove(object, start, end)
634 register vm_object_t object;
635 register vm_offset_t start;
636 register vm_offset_t end;
637{
638 register vm_page_t p;
639
640 if (object == NULL)
641 return;
642
643 vm_object_lock(object);
644 p = (vm_page_t) queue_first(&object->memq);
645 while (!queue_end(&object->memq, (queue_entry_t) p)) {
646 if ((start <= p->offset) && (p->offset < end))
647 pmap_page_protect(VM_PAGE_TO_PHYS(p), VM_PROT_NONE);
648 p = (vm_page_t) queue_next(&p->listq);
649 }
650 vm_object_unlock(object);
651}
652
653/*
654 * vm_object_copy:
655 *
656 * Create a new object which is a copy of an existing
657 * object, and mark all of the pages in the existing
658 * object 'copy-on-write'. The new object has one reference.
659 * Returns the new object.
660 *
661 * May defer the copy until later if the object is not backed
662 * up by a non-default pager.
663 */
664void vm_object_copy(src_object, src_offset, size,
665 dst_object, dst_offset, src_needs_copy)
666 register vm_object_t src_object;
667 vm_offset_t src_offset;
668 vm_size_t size;
669 vm_object_t *dst_object; /* OUT */
670 vm_offset_t *dst_offset; /* OUT */
671 boolean_t *src_needs_copy; /* OUT */
672{
673 register vm_object_t new_copy;
674 register vm_object_t old_copy;
675 vm_offset_t new_start, new_end;
676
677 register vm_page_t p;
678
679 if (src_object == NULL) {
680 /*
681 * Nothing to copy
682 */
683 *dst_object = NULL;
684 *dst_offset = 0;
685 *src_needs_copy = FALSE;
686 return;
687 }
688
689 /*
690 * If the object's pager is null_pager or the
691 * default pager, we don't have to make a copy
692 * of it. Instead, we set the needs copy flag and
693 * make a shadow later.
694 */
695
696 vm_object_lock(src_object);
45852188
DG
697
698/*
699 * we can simply add a reference to the object if we have no
700 * pager or are using the swap pager or we have an internal object
701 *
702 * John Dyson 24 Nov 93
703 */
15637ed4 704 if (src_object->pager == NULL ||
45852188
DG
705 (src_object->pager->pg_type == PG_SWAP) ||
706 src_object->internal) {
15637ed4
RG
707
708 /*
709 * Make another reference to the object
710 */
711 src_object->ref_count++;
712
713 /*
714 * Mark all of the pages copy-on-write.
715 */
716 for (p = (vm_page_t) queue_first(&src_object->memq);
717 !queue_end(&src_object->memq, (queue_entry_t)p);
718 p = (vm_page_t) queue_next(&p->listq)) {
719 if (src_offset <= p->offset &&
720 p->offset < src_offset + size)
721 p->copy_on_write = TRUE;
722 }
723 vm_object_unlock(src_object);
724
725 *dst_object = src_object;
726 *dst_offset = src_offset;
727
728 /*
729 * Must make a shadow when write is desired
730 */
731 *src_needs_copy = TRUE;
732 return;
733 }
734
735 /*
736 * Try to collapse the object before copying it.
737 */
738 vm_object_collapse(src_object);
739
740 /*
741 * If the object has a pager, the pager wants to
742 * see all of the changes. We need a copy-object
743 * for the changed pages.
744 *
745 * If there is a copy-object, and it is empty,
746 * no changes have been made to the object since the
747 * copy-object was made. We can use the same copy-
748 * object.
749 */
750
751 Retry1:
752 old_copy = src_object->copy;
753 if (old_copy != NULL) {
754 /*
755 * Try to get the locks (out of order)
756 */
757 if (!vm_object_lock_try(old_copy)) {
758 vm_object_unlock(src_object);
759
760 /* should spin a bit here... */
761 vm_object_lock(src_object);
762 goto Retry1;
763 }
764
765 if (old_copy->resident_page_count == 0 &&
766 old_copy->pager == NULL) {
767 /*
768 * Return another reference to
769 * the existing copy-object.
770 */
771 old_copy->ref_count++;
772 vm_object_unlock(old_copy);
773 vm_object_unlock(src_object);
774 *dst_object = old_copy;
775 *dst_offset = src_offset;
776 *src_needs_copy = FALSE;
777 return;
778 }
779 vm_object_unlock(old_copy);
780 }
781 vm_object_unlock(src_object);
782
783 /*
784 * If the object has a pager, the pager wants
785 * to see all of the changes. We must make
786 * a copy-object and put the changed pages there.
787 *
788 * The copy-object is always made large enough to
789 * completely shadow the original object, since
790 * it may have several users who want to shadow
791 * the original object at different points.
792 */
793
794 new_copy = vm_object_allocate(src_object->size);
795
796 Retry2:
797 vm_object_lock(src_object);
798 /*
799 * Copy object may have changed while we were unlocked
800 */
801 old_copy = src_object->copy;
802 if (old_copy != NULL) {
803 /*
804 * Try to get the locks (out of order)
805 */
806 if (!vm_object_lock_try(old_copy)) {
807 vm_object_unlock(src_object);
808 goto Retry2;
809 }
810
811 /*
812 * Consistency check
813 */
814 if (old_copy->shadow != src_object ||
815 old_copy->shadow_offset != (vm_offset_t) 0)
816 panic("vm_object_copy: copy/shadow inconsistency");
817
818 /*
819 * Make the old copy-object shadow the new one.
820 * It will receive no more pages from the original
821 * object.
822 */
823
824 src_object->ref_count--; /* remove ref. from old_copy */
825 old_copy->shadow = new_copy;
826 new_copy->ref_count++; /* locking not needed - we
827 have the only pointer */
828 vm_object_unlock(old_copy); /* done with old_copy */
829 }
830
831 new_start = (vm_offset_t) 0; /* always shadow original at 0 */
832 new_end = (vm_offset_t) new_copy->size; /* for the whole object */
833
834 /*
835 * Point the new copy at the existing object.
836 */
837
838 new_copy->shadow = src_object;
839 new_copy->shadow_offset = new_start;
840 src_object->ref_count++;
841 src_object->copy = new_copy;
842
843 /*
844 * Mark all the affected pages of the existing object
845 * copy-on-write.
846 */
847 p = (vm_page_t) queue_first(&src_object->memq);
848 while (!queue_end(&src_object->memq, (queue_entry_t) p)) {
849 if ((new_start <= p->offset) && (p->offset < new_end))
850 p->copy_on_write = TRUE;
851 p = (vm_page_t) queue_next(&p->listq);
852 }
853
854 vm_object_unlock(src_object);
855
856 *dst_object = new_copy;
857 *dst_offset = src_offset - new_start;
858 *src_needs_copy = FALSE;
859}
860
861/*
862 * vm_object_shadow:
863 *
864 * Create a new object which is backed by the
865 * specified existing object range. The source
866 * object reference is deallocated.
867 *
868 * The new object and offset into that object
869 * are returned in the source parameters.
870 */
871
872void vm_object_shadow(object, offset, length)
873 vm_object_t *object; /* IN/OUT */
874 vm_offset_t *offset; /* IN/OUT */
875 vm_size_t length;
876{
877 register vm_object_t source;
878 register vm_object_t result;
879
880 source = *object;
881
882 /*
883 * Allocate a new object with the given length
884 */
885
886 if ((result = vm_object_allocate(length)) == NULL)
887 panic("vm_object_shadow: no object for shadowing");
888
889 /*
890 * The new object shadows the source object, adding
891 * a reference to it. Our caller changes his reference
892 * to point to the new object, removing a reference to
893 * the source object. Net result: no change of reference
894 * count.
895 */
896 result->shadow = source;
897
898 /*
899 * Store the offset into the source object,
900 * and fix up the offset into the new object.
901 */
902
903 result->shadow_offset = *offset;
904
905 /*
906 * Return the new things
907 */
908
909 *offset = 0;
910 *object = result;
911}
912
913/*
914 * Set the specified object's pager to the specified pager.
915 */
916
917void vm_object_setpager(object, pager, paging_offset,
918 read_only)
919 vm_object_t object;
920 vm_pager_t pager;
921 vm_offset_t paging_offset;
922 boolean_t read_only;
923{
924#ifdef lint
925 read_only++; /* No longer used */
926#endif lint
927
928 vm_object_lock(object); /* XXX ? */
929 object->pager = pager;
930 object->paging_offset = paging_offset;
931 vm_object_unlock(object); /* XXX ? */
932}
933
934/*
935 * vm_object_hash hashes the pager/id pair.
936 */
937
938#define vm_object_hash(pager) \
939 (((unsigned)pager)%VM_OBJECT_HASH_COUNT)
940
941/*
942 * vm_object_lookup looks in the object cache for an object with the
943 * specified pager and paging id.
944 */
945
946vm_object_t vm_object_lookup(pager)
947 vm_pager_t pager;
948{
949 register queue_t bucket;
950 register vm_object_hash_entry_t entry;
951 vm_object_t object;
952
953 bucket = &vm_object_hashtable[vm_object_hash(pager)];
954
955 vm_object_cache_lock();
956
957 entry = (vm_object_hash_entry_t) queue_first(bucket);
958 while (!queue_end(bucket, (queue_entry_t) entry)) {
959 object = entry->object;
960 if (object->pager == pager) {
961 vm_object_lock(object);
962 if (object->ref_count == 0) {
963 queue_remove(&vm_object_cached_list, object,
964 vm_object_t, cached_list);
965 vm_object_cached--;
966 }
967 object->ref_count++;
968 vm_object_unlock(object);
969 vm_object_cache_unlock();
970 return(object);
971 }
972 entry = (vm_object_hash_entry_t) queue_next(&entry->hash_links);
973 }
974
975 vm_object_cache_unlock();
976 return(NULL);
977}
978
979/*
980 * vm_object_enter enters the specified object/pager/id into
981 * the hash table.
982 */
983
984void vm_object_enter(object, pager)
985 vm_object_t object;
986 vm_pager_t pager;
987{
988 register queue_t bucket;
989 register vm_object_hash_entry_t entry;
990
991 /*
992 * We don't cache null objects, and we can't cache
993 * objects with the null pager.
994 */
995
996 if (object == NULL)
997 return;
998 if (pager == NULL)
999 return;
1000
1001 bucket = &vm_object_hashtable[vm_object_hash(pager)];
1002 entry = (vm_object_hash_entry_t)
1003 malloc((u_long)sizeof *entry, M_VMOBJHASH, M_WAITOK);
1004 entry->object = object;
1005 object->can_persist = TRUE;
1006
1007 vm_object_cache_lock();
1008 queue_enter(bucket, entry, vm_object_hash_entry_t, hash_links);
1009 vm_object_cache_unlock();
1010}
1011
1012/*
1013 * vm_object_remove:
1014 *
1015 * Remove the pager from the hash table.
1016 * Note: This assumes that the object cache
1017 * is locked. XXX this should be fixed
1018 * by reorganizing vm_object_deallocate.
1019 */
4c45483e 1020static void
15637ed4
RG
1021vm_object_remove(pager)
1022 register vm_pager_t pager;
1023{
1024 register queue_t bucket;
1025 register vm_object_hash_entry_t entry;
1026 register vm_object_t object;
1027
1028 bucket = &vm_object_hashtable[vm_object_hash(pager)];
1029
1030 entry = (vm_object_hash_entry_t) queue_first(bucket);
1031 while (!queue_end(bucket, (queue_entry_t) entry)) {
1032 object = entry->object;
1033 if (object->pager == pager) {
1034 queue_remove(bucket, entry, vm_object_hash_entry_t,
1035 hash_links);
1036 free((caddr_t)entry, M_VMOBJHASH);
1037 break;
1038 }
1039 entry = (vm_object_hash_entry_t) queue_next(&entry->hash_links);
1040 }
1041}
1042
1043/*
1044 * vm_object_cache_clear removes all objects from the cache.
1045 *
1046 */
1047
1048void vm_object_cache_clear()
1049{
1050 register vm_object_t object;
1051
1052 /*
1053 * Remove each object in the cache by scanning down the
1054 * list of cached objects.
1055 */
1056 vm_object_cache_lock();
1057 while (!queue_empty(&vm_object_cached_list)) {
1058 object = (vm_object_t) queue_first(&vm_object_cached_list);
1059 vm_object_cache_unlock();
1060
1061 /*
1062 * Note: it is important that we use vm_object_lookup
1063 * to gain a reference, and not vm_object_reference, because
1064 * the logic for removing an object from the cache lies in
1065 * lookup.
1066 */
1067 if (object != vm_object_lookup(object->pager))
1068 panic("vm_object_cache_clear: I'm sooo confused.");
1069 pager_cache(object, FALSE);
1070
1071 vm_object_cache_lock();
1072 }
1073 vm_object_cache_unlock();
1074}
1075
1076boolean_t vm_object_collapse_allowed = TRUE;
1077/*
1078 * vm_object_collapse:
1079 *
1080 * Collapse an object with the object backing it.
1081 * Pages in the backing object are moved into the
1082 * parent, and the backing object is deallocated.
1083 *
1084 * Requires that the object be locked and the page
1085 * queues be unlocked.
1086 *
1087 */
1088void vm_object_collapse(object)
1089 register vm_object_t object;
1090
1091{
1092 register vm_object_t backing_object;
1093 register vm_offset_t backing_offset;
1094 register vm_size_t size;
1095 register vm_offset_t new_offset;
1096 register vm_page_t p, pp;
1097
1098 if (!vm_object_collapse_allowed)
1099 return;
1100
1101 while (TRUE) {
1102 /*
1103 * Verify that the conditions are right for collapse:
1104 *
1105 * The object exists and no pages in it are currently
1106 * being paged out (or have ever been paged out).
1107 */
1108 if (object == NULL ||
1109 object->paging_in_progress != 0 ||
1110 object->pager != NULL)
1111 return;
1112
1113 /*
1114 * There is a backing object, and
1115 */
1116
1117 if ((backing_object = object->shadow) == NULL)
1118 return;
1119
1120 vm_object_lock(backing_object);
1121 /*
1122 * ...
1123 * The backing object is not read_only,
1124 * and no pages in the backing object are
1125 * currently being paged out.
1126 * The backing object is internal.
1127 */
1128
1129 if (!backing_object->internal ||
1130 backing_object->paging_in_progress != 0) {
1131 vm_object_unlock(backing_object);
1132 return;
1133 }
1134
1135 /*
1136 * The backing object can't be a copy-object:
1137 * the shadow_offset for the copy-object must stay
1138 * as 0. Furthermore (for the 'we have all the
1139 * pages' case), if we bypass backing_object and
1140 * just shadow the next object in the chain, old
1141 * pages from that object would then have to be copied
1142 * BOTH into the (former) backing_object and into the
1143 * parent object.
1144 */
1145 if (backing_object->shadow != NULL &&
1146 backing_object->shadow->copy != NULL) {
1147 vm_object_unlock(backing_object);
1148 return;
1149 }
1150
1151 /*
1152 * We know that we can either collapse the backing
1153 * object (if the parent is the only reference to
1154 * it) or (perhaps) remove the parent's reference
1155 * to it.
1156 */
1157
1158 backing_offset = object->shadow_offset;
1159 size = object->size;
1160
1161 /*
1162 * If there is exactly one reference to the backing
1163 * object, we can collapse it into the parent.
1164 */
1165
1166 if (backing_object->ref_count == 1) {
1167
1168 /*
1169 * We can collapse the backing object.
1170 *
1171 * Move all in-memory pages from backing_object
1172 * to the parent. Pages that have been paged out
1173 * will be overwritten by any of the parent's
1174 * pages that shadow them.
1175 */
1176
1177 while (!queue_empty(&backing_object->memq)) {
1178
1179 p = (vm_page_t)
1180 queue_first(&backing_object->memq);
1181
1182 new_offset = (p->offset - backing_offset);
1183
1184 /*
1185 * If the parent has a page here, or if
1186 * this page falls outside the parent,
1187 * dispose of it.
1188 *
1189 * Otherwise, move it as planned.
1190 */
1191
1192 if (p->offset < backing_offset ||
1193 new_offset >= size) {
1194 vm_page_lock_queues();
1195 vm_page_free(p);
1196 vm_page_unlock_queues();
1197 } else {
1198 pp = vm_page_lookup(object, new_offset);
1199 if (pp != NULL && !pp->fake) {
1200 vm_page_lock_queues();
1201 vm_page_free(p);
1202 vm_page_unlock_queues();
1203 }
1204 else {
1205 if (pp) {
8820571b
NW
1206#if 1
1207 /*
1208 * This should never happen -- the
1209 * parent cannot have ever had an
1210 * external memory object, and thus
1211 * cannot have absent pages.
1212 */
1213 panic("vm_object_collapse: bad case");
1214 /* andrew@werple.apana.org.au - from
1215 mach 3.0 VM */
1216#else
15637ed4
RG
1217 /* may be someone waiting for it */
1218 PAGE_WAKEUP(pp);
1219 vm_page_lock_queues();
1220 vm_page_free(pp);
1221 vm_page_unlock_queues();
8820571b 1222#endif
15637ed4 1223 }
8820571b
NW
1224 /*
1225 * Parent now has no page.
1226 * Move the backing object's page
1227 * up.
1228 */
15637ed4
RG
1229 vm_page_rename(p, object, new_offset);
1230 }
1231 }
1232 }
1233
1234 /*
1235 * Move the pager from backing_object to object.
1236 *
1237 * XXX We're only using part of the paging space
1238 * for keeps now... we ought to discard the
1239 * unused portion.
1240 */
1241
e475daaa
JH
1242 /*
1243 * Remove backing_object from the object hashtable now.
1244 * This is necessary since its pager is going away
1245 * and therefore it is not going to be removed from
1246 * hashtable in vm_object_deallocate().
1247 *
1248 * NOTE - backing_object can only get at this stage if
1249 * it has an internal pager. It is not normally on the
1250 * hashtable unless it was put there by eg. vm_mmap()
1251 *
1252 * XXX - Need I worry here about *named* ANON pagers ?
1253 */
1254
1255 if (backing_object->pager) {
1256 vm_object_remove(backing_object->pager);
1257 }
15637ed4 1258 object->pager = backing_object->pager;
8820571b
NW
1259#if 1
1260 /* Mach 3.0 code */
1261 /* andrew@werple.apana.org.au, 12 Feb 1993 */
1262
1263 /*
1264 * If there is no pager, leave paging-offset alone.
1265 */
1266 if (object->pager)
1267 object->paging_offset =
1268 backing_object->paging_offset +
1269 backing_offset;
1270#else
1271 /* old VM 2.5 version */
15637ed4 1272 object->paging_offset += backing_offset;
8820571b 1273#endif
15637ed4
RG
1274
1275 backing_object->pager = NULL;
1276
1277 /*
1278 * Object now shadows whatever backing_object did.
1279 * Note that the reference to backing_object->shadow
1280 * moves from within backing_object to within object.
1281 */
1282
1283 object->shadow = backing_object->shadow;
1284 object->shadow_offset += backing_object->shadow_offset;
1285 if (object->shadow != NULL &&
1286 object->shadow->copy != NULL) {
1287 panic("vm_object_collapse: we collapsed a copy-object!");
1288 }
1289 /*
1290 * Discard backing_object.
1291 *
1292 * Since the backing object has no pages, no
1293 * pager left, and no object references within it,
1294 * all that is necessary is to dispose of it.
1295 */
1296
1297 vm_object_unlock(backing_object);
1298
1299 simple_lock(&vm_object_list_lock);
1300 queue_remove(&vm_object_list, backing_object,
1301 vm_object_t, object_list);
1302 vm_object_count--;
1303 simple_unlock(&vm_object_list_lock);
1304
1305 free((caddr_t)backing_object, M_VMOBJ);
1306
1307 object_collapses++;
1308 }
1309 else {
1310 /*
1311 * If all of the pages in the backing object are
1312 * shadowed by the parent object, the parent
1313 * object no longer has to shadow the backing
1314 * object; it can shadow the next one in the
1315 * chain.
1316 *
1317 * The backing object must not be paged out - we'd
1318 * have to check all of the paged-out pages, as
1319 * well.
1320 */
1321
1322 if (backing_object->pager != NULL) {
1323 vm_object_unlock(backing_object);
1324 return;
1325 }
1326
1327 /*
1328 * Should have a check for a 'small' number
1329 * of pages here.
1330 */
1331
1332 p = (vm_page_t) queue_first(&backing_object->memq);
1333 while (!queue_end(&backing_object->memq,
1334 (queue_entry_t) p)) {
1335
1336 new_offset = (p->offset - backing_offset);
1337
1338 /*
1339 * If the parent has a page here, or if
1340 * this page falls outside the parent,
1341 * keep going.
1342 *
1343 * Otherwise, the backing_object must be
1344 * left in the chain.
1345 */
1346
1347 if (p->offset >= backing_offset &&
1348 new_offset <= size &&
1349 ((pp = vm_page_lookup(object, new_offset))
1350 == NULL ||
1351 pp->fake)) {
1352 /*
1353 * Page still needed.
1354 * Can't go any further.
1355 */
1356 vm_object_unlock(backing_object);
1357 return;
1358 }
1359 p = (vm_page_t) queue_next(&p->listq);
1360 }
1361
1362 /*
1363 * Make the parent shadow the next object
1364 * in the chain. Deallocating backing_object
1365 * will not remove it, since its reference
1366 * count is at least 2.
1367 */
1368
1369 vm_object_reference(object->shadow = backing_object->shadow);
1370 object->shadow_offset += backing_object->shadow_offset;
1371
8820571b
NW
1372#if 1
1373 /* Mach 3.0 code */
1374 /* andrew@werple.apana.org.au, 12 Feb 1993 */
1375
1376 /*
1377 * Backing object might have had a copy pointer
1378 * to us. If it did, clear it.
1379 */
1380 if (backing_object->copy == object)
1381 backing_object->copy = NULL;
1382#endif
1383
15637ed4
RG
1384 /* Drop the reference count on backing_object.
1385 * Since its ref_count was at least 2, it
1386 * will not vanish; so we don't need to call
1387 * vm_object_deallocate.
1388 */
1389 backing_object->ref_count--;
1390 vm_object_unlock(backing_object);
1391
1392 object_bypasses ++;
1393
1394 }
1395
1396 /*
1397 * Try again with this object's new backing object.
1398 */
1399 }
1400}
1401
1402/*
1403 * vm_object_page_remove: [internal]
1404 *
1405 * Removes all physical pages in the specified
1406 * object range from the object's list of pages.
1407 *
1408 * The object must be locked.
1409 */
1410void vm_object_page_remove(object, start, end)
1411 register vm_object_t object;
1412 register vm_offset_t start;
1413 register vm_offset_t end;
1414{
1415 register vm_page_t p, next;
1416
1417 if (object == NULL)
1418 return;
1419
1420 p = (vm_page_t) queue_first(&object->memq);
1421 while (!queue_end(&object->memq, (queue_entry_t) p)) {
1422 next = (vm_page_t) queue_next(&p->listq);
1423 if ((start <= p->offset) && (p->offset < end)) {
1424 pmap_page_protect(VM_PAGE_TO_PHYS(p), VM_PROT_NONE);
1425 vm_page_lock_queues();
1426 vm_page_free(p);
1427 vm_page_unlock_queues();
1428 }
1429 p = next;
1430 }
1431}
1432
1433/*
1434 * Routine: vm_object_coalesce
1435 * Function: Coalesces two objects backing up adjoining
1436 * regions of memory into a single object.
1437 *
1438 * returns TRUE if objects were combined.
1439 *
1440 * NOTE: Only works at the moment if the second object is NULL -
1441 * if it's not, which object do we lock first?
1442 *
1443 * Parameters:
1444 * prev_object First object to coalesce
1445 * prev_offset Offset into prev_object
1446 * next_object Second object into coalesce
1447 * next_offset Offset into next_object
1448 *
1449 * prev_size Size of reference to prev_object
1450 * next_size Size of reference to next_object
1451 *
1452 * Conditions:
1453 * The object must *not* be locked.
1454 */
1455boolean_t vm_object_coalesce(prev_object, next_object,
1456 prev_offset, next_offset,
1457 prev_size, next_size)
1458
1459 register vm_object_t prev_object;
1460 vm_object_t next_object;
1461 vm_offset_t prev_offset, next_offset;
1462 vm_size_t prev_size, next_size;
1463{
1464 vm_size_t newsize;
1465
1466#ifdef lint
1467 next_offset++;
1468#endif lint
1469
1470 if (next_object != NULL) {
1471 return(FALSE);
1472 }
1473
1474 if (prev_object == NULL) {
1475 return(TRUE);
1476 }
1477
1478 vm_object_lock(prev_object);
1479
1480 /*
1481 * Try to collapse the object first
1482 */
1483 vm_object_collapse(prev_object);
1484
1485 /*
1486 * Can't coalesce if:
1487 * . more than one reference
1488 * . paged out
1489 * . shadows another object
1490 * . has a copy elsewhere
1491 * (any of which mean that the pages not mapped to
1492 * prev_entry may be in use anyway)
1493 */
1494
1495 if (prev_object->ref_count > 1 ||
1496 prev_object->pager != NULL ||
1497 prev_object->shadow != NULL ||
1498 prev_object->copy != NULL) {
1499 vm_object_unlock(prev_object);
1500 return(FALSE);
1501 }
1502
1503 /*
1504 * Remove any pages that may still be in the object from
1505 * a previous deallocation.
1506 */
1507
1508 vm_object_page_remove(prev_object,
1509 prev_offset + prev_size,
1510 prev_offset + prev_size + next_size);
1511
1512 /*
1513 * Extend the object if necessary.
1514 */
1515 newsize = prev_offset + prev_size + next_size;
1516 if (newsize > prev_object->size)
1517 prev_object->size = newsize;
1518
1519 vm_object_unlock(prev_object);
1520 return(TRUE);
1521}
1522
d55b6cf4 1523#if defined(DEBUG) || (NDDB > 0)
15637ed4
RG
1524/*
1525 * vm_object_print: [ debug ]
1526 */
1527void vm_object_print(object, full)
1528 vm_object_t object;
1529 boolean_t full;
1530{
1531 register vm_page_t p;
1532 extern indent;
1533
1534 register int count;
1535
1536 if (object == NULL)
1537 return;
1538
1539 iprintf("Object 0x%x: size=0x%x, res=%d, ref=%d, ",
1540 (int) object, (int) object->size,
1541 object->resident_page_count, object->ref_count);
1542 printf("pager=0x%x+0x%x, shadow=(0x%x)+0x%x\n",
1543 (int) object->pager, (int) object->paging_offset,
1544 (int) object->shadow, (int) object->shadow_offset);
1545 printf("cache: next=0x%x, prev=0x%x\n",
1546 object->cached_list.next, object->cached_list.prev);
1547
1548 if (!full)
1549 return;
1550
1551 indent += 2;
1552 count = 0;
1553 p = (vm_page_t) queue_first(&object->memq);
1554 while (!queue_end(&object->memq, (queue_entry_t) p)) {
1555 if (count == 0)
1556 iprintf("memory:=");
1557 else if (count == 6) {
1558 printf("\n");
1559 iprintf(" ...");
1560 count = 0;
1561 } else
1562 printf(",");
1563 count++;
1564
1565 printf("(off=0x%x,page=0x%x)", p->offset, VM_PAGE_TO_PHYS(p));
1566 p = (vm_page_t) queue_next(&p->listq);
1567 }
1568 if (count != 0)
1569 printf("\n");
1570 indent -= 2;
1571}
d55b6cf4 1572#endif /* defined(DEBUG) || (NDDB > 0) */