summaryrefslogtreecommitdiffstats
path: root/sys
diff options
context:
space:
mode:
authorfsmp <fsmp@FreeBSD.org>1997-08-15 02:33:30 +0000
committerfsmp <fsmp@FreeBSD.org>1997-08-15 02:33:30 +0000
commit36308aa29178c52ad643e626f7958ca47754d53c (patch)
treee856ea87dccd37655beffa7e303a3608f17be38e /sys
parentb458c644f830ba84395a5e62c9236cb430c4f682 (diff)
downloadFreeBSD-src-36308aa29178c52ad643e626f7958ca47754d53c.zip
FreeBSD-src-36308aa29178c52ad643e626f7958ca47754d53c.tar.gz
The promised "better fix" for "Trap 9 When Boot SMP" problem.
We now tsleep() in kthread_init() between start_init() and prepare_usermode() while waiting for ALL the idle_loop() processes to come online. Debugged & tested by: "Thomas D. Dean" <tomdean@ix.netcom.com> Reviewed by: David Greenman <dg@root.com>
Diffstat (limited to 'sys')
-rw-r--r--sys/kern/init_main.c12
-rw-r--r--sys/kern/init_smp.c35
2 files changed, 18 insertions, 29 deletions
diff --git a/sys/kern/init_main.c b/sys/kern/init_main.c
index 451c66a..90c113c 100644
--- a/sys/kern/init_main.c
+++ b/sys/kern/init_main.c
@@ -39,7 +39,7 @@
* SUCH DAMAGE.
*
* @(#)init_main.c 8.9 (Berkeley) 1/21/94
- * $Id: init_main.c,v 1.67 1997/08/05 00:01:21 dyson Exp $
+ * $Id: init_main.c,v 1.5 1997/08/15 02:13:31 smp Exp smp $
*/
#include "opt_rlimit.h"
@@ -62,6 +62,9 @@
#include <sys/vmmeter.h>
#include <machine/cpu.h>
+#ifdef SMP
+#include <machine/smp.h>
+#endif /* SMP */
#include <vm/vm.h>
#include <vm/vm_param.h>
@@ -535,10 +538,15 @@ static void
kthread_init(dummy)
void *dummy;
{
-
/* Create process 1 (init(8)). */
start_init(curproc);
+#ifdef SMP
+ /* wait for the SMP idle loops to come online */
+ while (smp_idle_loops < mp_ncpus)
+ tsleep((caddr_t *)&smp_idle_loops, PWAIT, "smpilw", 0);
+#endif /* SMP */
+
prepare_usermode();
/*
diff --git a/sys/kern/init_smp.c b/sys/kern/init_smp.c
index 191cdc3..6d56a60 100644
--- a/sys/kern/init_smp.c
+++ b/sys/kern/init_smp.c
@@ -22,7 +22,7 @@
* OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
* SUCH DAMAGE.
*
- * $Id: init_smp.c,v 1.13 1997/07/22 16:49:54 fsmp Exp $
+ * $Id: init_smp.c,v 1.10 1997/08/15 02:13:31 smp Exp smp $
*/
#include "opt_smp.h"
@@ -44,7 +44,7 @@
#include <machine/cpu.h>
#include <machine/smp.h>
-#include <machine/smptests.h> /** IGNORE_IDLEPROCS, TEST_TEST1 */
+#include <machine/smptests.h> /** IGNORE_IDLEPROCS */
#include <machine/specialreg.h>
#include <vm/vm.h>
@@ -54,10 +54,6 @@
#include <vm/vm_map.h>
#include <sys/user.h>
-#if defined(TEST_TEST1)
-void ipi_test1(void);
-#endif /** TEST_TEST1 */
-
int smp_active = 0; /* are the APs allowed to run? */
static int
@@ -108,7 +104,7 @@ static void smp_idleloop __P((void *));
void secondary_main __P((void));
-static int idle_loops = 0;
+volatile int smp_idle_loops = 0;
void boot_unlock __P((void));
struct proc *SMPidleproc[NCPU];
@@ -134,7 +130,6 @@ smp_kickoff(dummy)
SMPidleproc[i] = p;
p->p_flag |= P_INMEM | P_SYSTEM | P_IDLEPROC;
sprintf(p->p_comm, "cpuidle%d", i);
-
/*
* PRIO_IDLE is the last scheduled of the three
* classes and we choose the lowest priority possible
@@ -186,15 +181,7 @@ secondary_main()
printf("SMP: AP CPU #%d LAUNCHED!! Starting Scheduling...\n",
cpuid);
-#if defined(TEST_TEST1)
-/* XXX this would be dangerous for > 2 CPUs! */
- if (cpuid == IPI_TARGET_TEST1) {
- lapic.tpr = 0xff;
- ipi_test1();
- }
-#endif /** TEST_TEST1 */
-
- /* Setup the FPU. */
+ /* XXX FIXME: i386 specific, and redundant: Setup the FPU. */
load_cr0((rcr0() & ~CR0_EM) | CR0_MP | CR0_NE | CR0_TS);
curproc = NULL; /* ensure no context to save */
@@ -215,24 +202,18 @@ void *dummy;
int dcnt = 0;
int apic_id;
-#if 1
- /*
- * XXX FIXME: cheap fix for "trap 9 on boot" problem.
- * this is temporary, but seems to be the most benign of our choices.
- * expected to be fixed properly "real soon now".
- */
- asm("pushl %ds; popl %es");
-#endif
-
/*
* This code is executed only on startup of the idleprocs
* The fact that this is executed is an indication that the
* idle procs are online and it's safe to kick off the first
* AP cpu.
*/
- if ( ++idle_loops == mp_ncpus ) {
+ if ( ++smp_idle_loops == mp_ncpus ) {
printf("SMP: All idle procs online.\n");
+ /* let the init process finish */
+ wakeup((caddr_t *)&smp_idle_loops);
+
#ifndef NO_AUTOSTART
printf("SMP: *** AUTO *** starting 1st AP!\n");
smp_cpus = 1;
OpenPOWER on IntegriCloud