Skip site navigation (1)Skip section navigation (2)
Date:      Wed, 28 Dec 2016 04:48:30 +0000 (UTC)
From:      Konstantin Belousov <kib@FreeBSD.org>
To:        src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-stable@freebsd.org, svn-src-stable-11@freebsd.org
Subject:   svn commit: r310659 - in stable/11/sys: amd64/amd64 i386/i386
Message-ID:  <201612280448.uBS4mUqI093734@repo.freebsd.org>

next in thread | raw e-mail | index | archive | help
Author: kib
Date: Wed Dec 28 04:48:30 2016
New Revision: 310659
URL: https://svnweb.freebsd.org/changeset/base/310659

Log:
  MFC r304957, r304958,  r306310 (by bde):
  Fix vm86 initialization.
  
  MFC r310050:
  Improve very early trap handling on amd64.

Modified:
  stable/11/sys/amd64/amd64/machdep.c
  stable/11/sys/i386/i386/machdep.c
Directory Properties:
  stable/11/   (props changed)

Modified: stable/11/sys/amd64/amd64/machdep.c
==============================================================================
--- stable/11/sys/amd64/amd64/machdep.c	Wed Dec 28 04:47:17 2016	(r310658)
+++ stable/11/sys/amd64/amd64/machdep.c	Wed Dec 28 04:48:30 2016	(r310659)
@@ -1506,6 +1506,16 @@ native_parse_preload_data(u_int64_t modu
 	return (kmdp);
 }
 
+static void
+amd64_kdb_init(void)
+{
+	kdb_init();
+#ifdef KDB
+	if (boothowto & RB_KDB)
+		kdb_enter(KDB_WHY_BOOTFLAGS, "Boot flags requested debugger");
+#endif
+}
+
 u_int64_t
 hammer_time(u_int64_t modulep, u_int64_t physfree)
 {
@@ -1517,6 +1527,7 @@ hammer_time(u_int64_t modulep, u_int64_t
 	u_int64_t msr;
 	char *env;
 	size_t kstack0_sz;
+	int late_console;
 
 	/*
  	 * This may be done better later if it gets more high level
@@ -1561,6 +1572,7 @@ hammer_time(u_int64_t modulep, u_int64_t
 	physfree += DPCPU_SIZE;
 	PCPU_SET(prvspace, pc);
 	PCPU_SET(curthread, &thread0);
+	/* Non-late cninit() and printf() can be moved up to here. */
 	PCPU_SET(tssp, &common_tss[0]);
 	PCPU_SET(commontssp, &common_tss[0]);
 	PCPU_SET(tss, (struct system_segment_descriptor *)&gdt[GPROC0_SEL]);
@@ -1660,12 +1672,36 @@ hammer_time(u_int64_t modulep, u_int64_t
 	wrmsr(MSR_STAR, msr);
 	wrmsr(MSR_SF_MASK, PSL_NT|PSL_T|PSL_I|PSL_C|PSL_D);
 
+	/*
+	 * Temporary forge some valid pointer to PCB, for exception
+	 * handlers.  It is reinitialized properly below after FPU is
+	 * set up.  Also set up td_critnest to short-cut the page
+	 * fault handler.
+	 */
+	cpu_max_ext_state_size = sizeof(struct savefpu);
+	thread0.td_pcb = get_pcb_td(&thread0);
+	thread0.td_critnest = 1;
+
+	/*
+	 * The console and kdb should be initialized even earlier than here,
+	 * but some console drivers don't work until after getmemsize().
+	 * Default to late console initialization to support these drivers.
+	 * This loses mainly printf()s in getmemsize() and early debugging.
+	 */
+	late_console = 1;
+	TUNABLE_INT_FETCH("debug.late_console", &late_console);
+	if (!late_console) {
+		cninit();
+		amd64_kdb_init();
+	}
+
 	getmemsize(kmdp, physfree);
 	init_param2(physmem);
 
 	/* now running on new page tables, configured,and u/iom is accessible */
 
-	cninit();
+	if (late_console)
+		cninit();
 
 #ifdef DEV_ISA
 #ifdef DEV_ATPIC
@@ -1686,13 +1722,8 @@ hammer_time(u_int64_t modulep, u_int64_t
 #error "have you forgotten the isa device?";
 #endif
 
-	kdb_init();
-
-#ifdef KDB
-	if (boothowto & RB_KDB)
-		kdb_enter(KDB_WHY_BOOTFLAGS,
-		    "Boot flags requested debugger");
-#endif
+	if (late_console)
+		amd64_kdb_init();
 
 	msgbufinit(msgbufp, msgbufsize);
 	fpuinit();
@@ -1741,6 +1772,7 @@ hammer_time(u_int64_t modulep, u_int64_t
 #ifdef FDT
 	x86_init_fdt();
 #endif
+	thread0.td_critnest = 0;
 
 	/* Location of kernel stack for locore */
 	return ((u_int64_t)thread0.td_pcb);

Modified: stable/11/sys/i386/i386/machdep.c
==============================================================================
--- stable/11/sys/i386/i386/machdep.c	Wed Dec 28 04:47:17 2016	(r310658)
+++ stable/11/sys/i386/i386/machdep.c	Wed Dec 28 04:48:30 2016	(r310659)
@@ -2089,7 +2089,6 @@ getmemsize(int first)
 	 * use that and do not make any VM86 calls.
 	 */
 	physmap_idx = 0;
-	smapbase = NULL;
 	kmdp = preload_search_by_type("elf kernel");
 	if (kmdp == NULL)
 		kmdp = preload_search_by_type("elf32 kernel");
@@ -2223,6 +2222,9 @@ physmap_done:
 	 * highest page of the physical address space.  It should be
 	 * called something like "Maxphyspage".  We may adjust this 
 	 * based on ``hw.physmem'' and the results of the memory test.
+	 *
+	 * This is especially confusing when it is much larger than the
+	 * memory size and is displayed as "realmem".
 	 */
 	Maxmem = atop(physmap[physmap_idx + 1]);
 
@@ -2428,6 +2430,19 @@ do_next:
 }
 #endif /* PC98 */
 
+static void
+i386_kdb_init(void)
+{
+#ifdef DDB
+	db_fetch_ksymtab(bootinfo.bi_symtab, bootinfo.bi_esymtab);
+#endif
+	kdb_init();
+#ifdef KDB
+	if (boothowto & RB_KDB)
+		kdb_enter(KDB_WHY_BOOTFLAGS, "Boot flags requested debugger");
+#endif
+}
+
 register_t
 init386(first)
 	int first;
@@ -2438,6 +2453,7 @@ init386(first)
 #ifdef CPU_ENABLE_SSE
 	struct xstate_hdr *xhdr;
 #endif
+	int late_console;
 
 	thread0.td_kstack = proc0kstack;
 	thread0.td_kstack_pages = TD0_KSTACK_PAGES;
@@ -2502,6 +2518,7 @@ init386(first)
 	first += DPCPU_SIZE;
 	PCPU_SET(prvspace, pc);
 	PCPU_SET(curthread, &thread0);
+	/* Non-late cninit() and printf() can be moved up to here. */
 
 	/*
 	 * Initialize mutexes.
@@ -2636,20 +2653,17 @@ init386(first)
 	dblfault_tss.tss_cs = GSEL(GCODE_SEL, SEL_KPL);
 	dblfault_tss.tss_ldt = GSEL(GLDT_SEL, SEL_KPL);
 
-	vm86_initialize();
-	getmemsize(first);
-	init_param2(physmem);
-
-	/* now running on new page tables, configured,and u/iom is accessible */
-
-	/*
-	 * Initialize the console before we print anything out.
-	 */
-	cninit();
-
-	if (metadata_missing)
-		printf("WARNING: loader(8) metadata is missing!\n");
+	/* Initialize the tss (except for the final esp0) early for vm86. */
+	PCPU_SET(common_tss.tss_esp0, thread0.td_kstack +
+	    thread0.td_kstack_pages * PAGE_SIZE - 16);
+	PCPU_SET(common_tss.tss_ss0, GSEL(GDATA_SEL, SEL_KPL));
+	gsel_tss = GSEL(GPROC0_SEL, SEL_KPL);
+	PCPU_SET(tss_gdt, &gdt[GPROC0_SEL].sd);
+	PCPU_SET(common_tssd, *PCPU_GET(tss_gdt));
+	PCPU_SET(common_tss.tss_ioopt, (sizeof (struct i386tss)) << 16);
+	ltr(gsel_tss);
 
+	/* Initialize the PIC early for vm86 calls. */
 #ifdef DEV_ISA
 #ifdef DEV_ATPIC
 #ifndef PC98
@@ -2671,16 +2685,33 @@ init386(first)
 #endif
 #endif
 
-#ifdef DDB
-	db_fetch_ksymtab(bootinfo.bi_symtab, bootinfo.bi_esymtab);
-#endif
+	/*
+	 * The console and kdb should be initialized even earlier than here,
+	 * but some console drivers don't work until after getmemsize().
+	 * Default to late console initialization to support these drivers.
+	 * This loses mainly printf()s in getmemsize() and early debugging.
+	 */
+	late_console = 1;
+	TUNABLE_INT_FETCH("debug.late_console", &late_console);
+	if (!late_console) {
+		cninit();
+		i386_kdb_init();
+	}
 
-	kdb_init();
+	vm86_initialize();
+	getmemsize(first);
+	init_param2(physmem);
 
-#ifdef KDB
-	if (boothowto & RB_KDB)
-		kdb_enter(KDB_WHY_BOOTFLAGS, "Boot flags requested debugger");
-#endif
+	/* now running on new page tables, configured,and u/iom is accessible */
+
+	if (late_console)
+		cninit();
+
+	if (metadata_missing)
+		printf("WARNING: loader(8) metadata is missing!\n");
+
+	if (late_console)
+		i386_kdb_init();
 
 	msgbufinit(msgbufp, msgbufsize);
 #ifdef DEV_NPX
@@ -2701,14 +2732,10 @@ init386(first)
 	}
 #endif
 	PCPU_SET(curpcb, thread0.td_pcb);
-	/* make an initial tss so cpu can get interrupt stack on syscall! */
+	/* Move esp0 in the tss to its final place. */
 	/* Note: -16 is so we can grow the trapframe if we came from vm86 */
 	PCPU_SET(common_tss.tss_esp0, (vm_offset_t)thread0.td_pcb - 16);
-	PCPU_SET(common_tss.tss_ss0, GSEL(GDATA_SEL, SEL_KPL));
-	gsel_tss = GSEL(GPROC0_SEL, SEL_KPL);
-	PCPU_SET(tss_gdt, &gdt[GPROC0_SEL].sd);
-	PCPU_SET(common_tssd, *PCPU_GET(tss_gdt));
-	PCPU_SET(common_tss.tss_ioopt, (sizeof (struct i386tss)) << 16);
+	gdt[GPROC0_SEL].sd.sd_type = SDT_SYS386TSS;	/* clear busy bit */
 	ltr(gsel_tss);
 
 	/* make a call gate to reenter kernel with */



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201612280448.uBS4mUqI093734>