Subject: port-amiga/1721: Amiga '040 MMU initialization will crash on certain configurations
To: None <gnats-bugs@gnats.netbsd.org>
From: None <osymh@gemini.oscs.montana.edu>
List: netbsd-bugs
Date: 11/03/1995 01:32:51
>Number:         1721
>Category:       port-amiga
>Synopsis:       68040 MMU setup with constant values crashes on some systems
>Confidential:   no
>Severity:       critical
>Priority:       high
>Responsible:    gnats-admin (GNATS administrator)
>State:          open
>Class:          sw-bug
>Submitter-Id:   net
>Arrival-Date:   Fri Nov  3 04:20:02 1995
>Last-Modified:
>Originator:     Michael L. Hitch
>Organization:
	Information Technology Center
	Montana State Univerisity
>Release:        <NetBSD-current source date>October 27, 1995
>Environment:
	
System: NetBSD amiga2.oscs.montana.edu 1.1_ALPHA NetBSD 1.1_ALPHA (ZEUS) #951027-0: Fri Oct 27 21:08:32 MDT 1995 root@amiga2.oscs.montana.edu:/opt/tmp/src/sys/arch/amiga/compile/ZEUS amiga


>Description:
	I forgot to fix the temporary use of constants for setting up the
	68040 MMU.  On systems that have large Zorro III address spaces,
	additional level 2 descriptor tables were initialized, and then
	later overwritten.
>How-To-Repeat:
	Try running NetBSD on an Amiga with a video board that uses 64MB
	of Zorro III address space.
>Fix:
	Apply the following patch to properly compute the level 2 descriptor
	table bit maps:

diff -cr /usr/src/sys/arch/amiga/amiga/amiga_init.c sys/arch/amiga/amiga/amiga_init.c
*** /usr/src/sys/arch/amiga/amiga/amiga_init.c	Fri Oct 13 19:40:45 1995
--- sys/arch/amiga/amiga/amiga_init.c	Fri Oct 27 19:33:57 1995
***************
*** 63,68 ****
--- 63,71 ----
  extern u_int	Sysptmap, Sysptsize, Sysseg, Umap, proc0paddr;
  extern u_int	Sysseg_pa;
  extern u_int	virtual_avail;
+ #ifdef M68040
+ extern int	protostfree;
+ #endif
  
  extern char *esym;
  
***************
*** 346,352 ****
  		 * Initialize level 2 descriptors (which immediately
  		 * follow the level 1 table).  We need:
  		 *	NPTEPG / SG4_LEV3SIZE
! 		 * level 2 descriptors to map eachof the nptpages + 1
  		 * pages of PTEs.  Note that we set the "used" bit
  		 * now to save the HW the expense of doing it.
  		 */
--- 349,355 ----
  		 * Initialize level 2 descriptors (which immediately
  		 * follow the level 1 table).  We need:
  		 *	NPTEPG / SG4_LEV3SIZE
! 		 * level 2 descriptors to map each of the nptpages + 1
  		 * pages of PTEs.  Note that we set the "used" bit
  		 * now to save the HW the expense of doing it.
  		 */
***************
*** 363,370 ****
  		 *	roundup(num, SG4_LEV2SIZE) / SG4_LEVEL2SIZE
  		 * level 1 descriptors to map the 'num' level 2's.
  		 */
  		sg = (u_int *) Sysseg_pa;
! 		esg = &sg[roundup(i, SG4_LEV2SIZE) / SG4_LEV2SIZE];
  		sg_proto = (u_int)&sg[SG4_LEV1SIZE] | SG_U | SG_RW |SG_V;
  		while (sg < esg) {
  			*sg++ = sg_proto;
--- 366,375 ----
  		 *	roundup(num, SG4_LEV2SIZE) / SG4_LEVEL2SIZE
  		 * level 1 descriptors to map the 'num' level 2's.
  		 */
+ 		i = roundup(i, SG4_LEV2SIZE) / SG4_LEV2SIZE;
+ 		protostfree = (-1 << (i + 1)) /* & ~(-1 << MAXKL2SIZE) */;
  		sg = (u_int *) Sysseg_pa;
! 		esg = &sg[i];
  		sg_proto = (u_int)&sg[SG4_LEV1SIZE] | SG_U | SG_RW |SG_V;
  		while (sg < esg) {
  			*sg++ = sg_proto;
diff -cr /usr/src/sys/arch/amiga/amiga/pmap.c sys/arch/amiga/amiga/pmap.c
*** /usr/src/sys/arch/amiga/amiga/pmap.c	Fri Oct 13 19:41:13 1995
--- sys/arch/amiga/amiga/pmap.c	Fri Oct 27 19:35:29 1995
***************
*** 237,242 ****
--- 237,243 ----
  char		*pmap_attributes;	/* reference and modify bits */
  #ifdef M68040
  static int	pmap_ishift;	/* segment table index shift */
+ int		protostfree;	/* prototype (default) free ST map */
  #endif
  
  #ifdef MACHINE_NONCONTIG
***************
*** 363,369 ****
  #ifdef M68040
  	if (mmutype == MMU_68040) {
  		pmap_ishift = SG4_SHIFT1;
! 		pmap_kernel()->pm_stfree = 0xfffffff8;	/* XXXX */
  	} else
  		pmap_ishift = SG_ISHIFT;
  #endif
--- 364,370 ----
  #ifdef M68040
  	if (mmutype == MMU_68040) {
  		pmap_ishift = SG4_SHIFT1;
! 		pmap_kernel()->pm_stfree = protostfree;
  	} else
  		pmap_ishift = SG_ISHIFT;
  #endif
***************
*** 574,579 ****
--- 575,586 ----
  		printf("pmap_init: pt_map [%x - %x)\n", addr, addr2);
  #endif
  
+ #ifdef M68040
+ 	if (mmutype == MMU_68040) {
+ 		protostfree = ~1 & ~(-1 << MAXUL2SIZE);
+ 	}
+ #endif
+ 
  	/*
  	 * Now it is safe to enable pv_table recording.
  	 */
***************
*** 734,740 ****
  	pmap->pm_stpa = Segtabzeropa;
  #ifdef M68040
  	if (mmutype == MMU_68040)
! 		pmap->pm_stfree = 0x0000fffe;	/* XXXX */
  #endif
  	pmap->pm_stchanged = TRUE;
  	pmap->pm_count = 1;
--- 741,747 ----
  	pmap->pm_stpa = Segtabzeropa;
  #ifdef M68040
  	if (mmutype == MMU_68040)
! 		pmap->pm_stfree = protostfree;
  #endif
  	pmap->pm_stchanged = TRUE;
  	pmap->pm_count = 1;
***************
*** 1011,1017 ****
  					ptpmap->pm_stpa = Segtabzeropa;
  #ifdef M68040
  					if (mmutype == MMU_68040)
! 						ptpmap->pm_stfree = 0x0000fffe; /* XXXX */
  #endif
  					ptpmap->pm_stchanged = TRUE;
  					/*
--- 1018,1024 ----
  					ptpmap->pm_stpa = Segtabzeropa;
  #ifdef M68040
  					if (mmutype == MMU_68040)
! 						ptpmap->pm_stfree = protostfree;
  #endif
  					ptpmap->pm_stchanged = TRUE;
  					/*
***************
*** 2046,2052 ****
  		    pmap_kernel(), (vm_offset_t)pmap->pm_stab);
  #ifdef M68040
  		if (mmutype == MMU_68040) {
! 			pmap->pm_stfree = 0x0000fffe;	/* XXXX */
  		}
  #endif
  		pmap->pm_stchanged = TRUE;
--- 2053,2059 ----
  		    pmap_kernel(), (vm_offset_t)pmap->pm_stab);
  #ifdef M68040
  		if (mmutype == MMU_68040) {
! 			pmap->pm_stfree = protostfree;
  		}
  #endif
  		pmap->pm_stchanged = TRUE;

>Audit-Trail:
>Unformatted: