diff options
author | alc <alc@FreeBSD.org> | 2003-10-17 05:07:17 +0000 |
---|---|---|
committer | alc <alc@FreeBSD.org> | 2003-10-17 05:07:17 +0000 |
commit | 29c05d8a9be4aa0fd6a6547fc436f4f6e4213cfe (patch) | |
tree | 76df340b810576199afed50fd6327b26c627e1db /sys/vm/vm_pageout.c | |
parent | c7a92905e0e1dfc49a03cf098b15b37735480078 (diff) | |
download | FreeBSD-src-29c05d8a9be4aa0fd6a6547fc436f4f6e4213cfe.zip FreeBSD-src-29c05d8a9be4aa0fd6a6547fc436f4f6e4213cfe.tar.gz |
- Synchronize access to a vm page's valid field using the containing
vm object's lock.
- Release the vm object and vm page queues locks around vput().
Diffstat (limited to 'sys/vm/vm_pageout.c')
-rw-r--r-- | sys/vm/vm_pageout.c | 33 |
1 files changed, 19 insertions, 14 deletions
diff --git a/sys/vm/vm_pageout.c b/sys/vm/vm_pageout.c index f0de2c2..2fc45fe 100644 --- a/sys/vm/vm_pageout.c +++ b/sys/vm/vm_pageout.c @@ -837,19 +837,23 @@ rescan0: } else { vm_page_dirty(m); } - - /* - * Invalid pages can be easily freed - */ + object = m->object; + if (!VM_OBJECT_TRYLOCK(object)) + continue; if (m->valid == 0) { - vm_pageout_page_free(m); + /* + * Invalid pages can be easily freed + */ + vm_page_busy(m); + pmap_remove_all(m); + vm_page_free(m); + cnt.v_dfree++; --page_shortage; - - /* - * Clean pages can be placed onto the cache queue. This - * effectively frees them. - */ } else if (m->dirty == 0) { + /* + * Clean pages can be placed onto the cache queue. + * This effectively frees them. + */ vm_page_cache(m); --page_shortage; } else if ((m->flags & PG_WINATCFLS) == 0 && pass == 0) { @@ -879,9 +883,6 @@ rescan0: struct vnode *vp = NULL; struct mount *mp; - object = m->object; - if (!VM_OBJECT_TRYLOCK(object)) - continue; if ((object->type != OBJT_SWAP) && (object->type != OBJT_DEFAULT)) { swap_pageouts_ok = 1; } else { @@ -1008,12 +1009,16 @@ rescan0: TAILQ_REMOVE(&vm_page_queues[PQ_INACTIVE].pl, &marker, pageq); splx(s); unlock_and_continue: + VM_OBJECT_UNLOCK(object); if (vp) { + vm_page_unlock_queues(); vput(vp); vn_finished_write(mp); + vm_page_lock_queues(); } - VM_OBJECT_UNLOCK(object); + continue; } + VM_OBJECT_UNLOCK(object); } /* |