svn commit: r323290 - head/sys/vm

Mark Johnston markj at FreeBSD.org
Thu Sep 14 20:32:42 UTC 2017


On Thu, Sep 14, 2017 at 09:51:17PM +0200, Andreas Tobler wrote:
> Hi Mark,
> 
> On 07.09.17 23:43, Mark Johnston wrote:
> > Author: markj
> > Date: Thu Sep  7 21:43:39 2017
> > New Revision: 323290
> > URL: https://svnweb.freebsd.org/changeset/base/323290
> > 
> > Log:
> >    Speed up vm_page_array initialization.
> >    
> >    We currently initialize the vm_page array in three passes: one to zero
> >    the array, one to initialize the "order" field of each page (necessary
> >    when inserting them into the vm_phys buddy allocator one-by-one), and
> >    one to initialize the remaining non-zero fields and individually insert
> >    each page into the allocator.
> >    
> >    Merge the three passes into one following a suggestion from alc:
> >    initialize vm_page fields in a single pass, and use vm_phys_free_contig()
> >    to efficiently insert physical memory segments into the buddy allocator.
> >    This reduces the initialization time to a third or a quarter of what it
> >    was before on most systems that I tested.
> >    
> >    Reviewed by:	alc, kib
> >    MFC after:	3 weeks
> >    Differential Revision:	https://reviews.freebsd.org/D12248
> > 
> > Modified:
> >    head/sys/vm/vm_page.c
> >    head/sys/vm/vm_phys.c
> >    head/sys/vm/vm_phys.h
> 
> I just found out that this commit breaks booting my powerpc64 Quad G5.
> It hangs, pressing ctrl-t shows: cmd: sh [*vm active pagequeue].
> 
> Sometimes it hangs earlier when the kbd is not there yet (usb), then I 
> can't get the process/task where it hangs.
> 
> Note, this kernel is compiled with the default gcc (4.2.1-FreeBSD)
> 
> Any ideas how to find out what's wrong?

Are you able to break into DDB when the hang occurs? If so, the output
of "show page" would be helpful.

Are you running with INVARIANTS configured? If not, please try that.

> The previous revision, r323289 seems stable, at least it survived 
> several kernel builds.

Could you apply the patch below and capture the first page or so of
output from after the kernel starts booting?

diff --git a/sys/vm/vm_page.c b/sys/vm/vm_page.c
index fda8d1cf37f7..6862195c3e9c 100644
--- a/sys/vm/vm_page.c
+++ b/sys/vm/vm_page.c
@@ -648,8 +648,11 @@ vm_page_startup(vm_offset_t vaddr)
 	 * Add physical memory segments corresponding to the available
 	 * physical pages.
 	 */
-	for (i = 0; phys_avail[i + 1] != 0; i += 2)
+	for (i = 0; phys_avail[i + 1] != 0; i += 2) {
+		printf("adding phys_avail seg %#jx - %#jx\n",
+		    phys_avail[i], phys_avail[i + 1]);
 		vm_phys_add_seg(phys_avail[i], phys_avail[i + 1]);
+	}
 
 	/*
 	 * Initialize the physical memory allocator.
@@ -664,6 +667,8 @@ vm_page_startup(vm_offset_t vaddr)
 	vm_cnt.v_free_count = 0;
 	for (segind = 0; segind < vm_phys_nsegs; segind++) {
 		seg = &vm_phys_segs[segind];
+		printf("inserting seg %d: %#jx - %#jx\n", segind,
+		    (uintmax_t)seg->start, (uintmax_t)seg->end);
 		for (pa = seg->start; pa < seg->end; pa += PAGE_SIZE)
 			vm_phys_init_page(pa);
 
@@ -679,6 +684,7 @@ vm_page_startup(vm_offset_t vaddr)
 			    seg->end > phys_avail[i + 1])
 				continue;
 
+			printf("inserting seg %d into vm_phys\n", segind);
 			m = seg->first_page;
 			pagecount = (u_long)atop(seg->end - seg->start);
 
@@ -694,6 +700,7 @@ vm_page_startup(vm_offset_t vaddr)
 			break;
 		}
 	}
+	printf("v_free_count: %u\n", vm_cnt.v_free_count);
 
 	/*
 	 * Remove blacklisted pages from the physical memory allocator.


More information about the svn-src-head mailing list