[parisc-linux-cvs] Patch to fix init fault on 64 bit kernel

John Marvin jsm@udlkern.fc.hp.com
Tue, 13 Feb 2001 04:57:13 -0700 (MST)


Here is a patch I just committed that fixes a bug that was manifesting itself
by causing init to fault forever on a 64 bit kernel. This patch removes
the mapping of a hp-ux gateway page into every process. This breaks
what little hp-ux compatibility there was (if it wasn't already broken).
The hp-ux gateway page support needs to be rewritten to only map a
gateway page into hp-ux processes.

John

--- arch/parisc/mm/init.c.old	Tue Feb 13 04:26:17 2001
+++ arch/parisc/mm/init.c	Tue Feb 13 04:29:42 2001
@@ -273,29 +273,21 @@ static void __init pagetable_init(void)
 	memset(empty_zero_page, 0, PAGE_SIZE);
 }
 
-unsigned long gateway_pgd_offset;
-unsigned long gateway_pgd_entry;
-
 static void __init gateway_init(void)
 {
-	unsigned long hpux_gateway_page_addr;
 	unsigned long linux_gateway_page_addr;
 	pgd_t *pg_dir;
 	pmd_t *pmd_base;
 	pmd_t *pmd;
 	pte_t *pg_table_base;
 	pte_t *pg_table;
-	/* FIXME: These are 'const' in order to trick the compiler
-           into not treating them as DP-relative data. */
-	extern void * const hpux_gateway_page;
+	/* FIXME: This is 'const' in order to trick the compiler
+	   into not treating it as DP-relative data. */
 	extern void * const linux_gateway_page;
 	pte_t pte;
 
-	hpux_gateway_page_addr = HPUX_GATEWAY_ADDR & PAGE_MASK;
 	linux_gateway_page_addr = LINUX_GATEWAY_ADDR & PAGE_MASK;
 
-	gateway_pgd_offset = hpux_gateway_page_addr >> PGDIR_SHIFT;
-
 	/*
 	 * Setup Linux Gateway page.
 	 *
@@ -332,47 +324,6 @@ static void __init gateway_init(void)
 
 	set_pte(pg_table,pte);
 
-	/*
-	 * Setup HP-UX gateway page.
-	 * This page will be aliased into each user address space.
-	 */
-
-	pg_table_base = (pte_t *) alloc_bootmem_pages(PAGE_SIZE);
-
-	pte = __mk_pte(__pa(&hpux_gateway_page), PAGE_GATEWAY);
-	pg_table = pg_table_base +
-		((hpux_gateway_page_addr & (PAGE_MASK) & (PMD_SIZE - 1)) >>
-								PAGE_SHIFT);
-
-	set_pte(pg_table,pte);
-
-
-#if PTRS_PER_PMD == 1
-	pmd_base = (pmd_t *)pg_table_base;
-#else
-	pmd_base = (pmd_t *) alloc_bootmem_pages(PAGE_SIZE);
-	pmd = pmd_base +
-		((hpux_gateway_page_addr & (PMD_MASK) & (PGDIR_SIZE - 1)) >>
-								PMD_SHIFT);
-	pmd_val(*pmd) = _PAGE_TABLE | __pa(pg_table_base);
-#endif
-
-	gateway_pgd_entry = _PAGE_TABLE | __pa(pmd_base);
-
-	/*
-	 * We will be aliasing the HP-UX gateway page into all HP-UX
-	 * user spaces at the same address (not counting the space register
-	 * value) that will be equivalently mapped as long as space register
-	 * hashing is disabled. It will be a problem if anyone touches
-	 * the gateway pages at its "kernel" address, since that is
-	 * NOT equivalently mapped. We'll flush the caches at this
-	 * point, just in case some code has touched those addresses
-	 * previous to this, but all bets are off if they get touched
-	 * after this point.
-	 */
-
-	flush_all_caches();
-
 	return;
 }
 
@@ -380,6 +331,7 @@ void __init paging_init(void)
 {
 	pagetable_init();
 	gateway_init();
+	flush_all_caches(); /* start with a known state */
 
 	{
 		unsigned long zones_size[MAX_NR_ZONES] = { max_pfn/2, max_pfn/2, };
--- include/asm-parisc/pgalloc.h.old	Tue Feb 13 04:24:09 2001
+++ include/asm-parisc/pgalloc.h	Tue Feb 13 04:25:16 2001
@@ -230,15 +230,10 @@ static inline void flush_tlb_range(struc
 
 extern __inline__ pgd_t *get_pgd_slow(void)
 {
-	extern unsigned long gateway_pgd_offset;
-	extern unsigned long gateway_pgd_entry;
 	pgd_t *ret = (pgd_t *)__get_free_page(GFP_KERNEL);
 
-	if (ret) {
+	if (ret)
 		memset (ret, 0, PTRS_PER_PGD * sizeof(pgd_t));
-		/* Install HP-UX and Linux gateway page translations */
-		pgd_val(*(ret + gateway_pgd_offset)) = gateway_pgd_entry;
-	}
 	return ret;
 }