From owner-freebsd-ppc@FreeBSD.ORG Thu Nov 11 02:50:09 2010 Return-Path: Delivered-To: freebsd-ppc@hub.freebsd.org Received: from mx1.freebsd.org (mx1.freebsd.org [IPv6:2001:4f8:fff6::34]) by hub.freebsd.org (Postfix) with ESMTP id 52970106564A for ; Thu, 11 Nov 2010 02:50:09 +0000 (UTC) (envelope-from gnats@FreeBSD.org) Received: from freefall.freebsd.org (freefall.freebsd.org [IPv6:2001:4f8:fff6::28]) by mx1.freebsd.org (Postfix) with ESMTP id 2628E8FC13 for ; Thu, 11 Nov 2010 02:50:09 +0000 (UTC) Received: from freefall.freebsd.org (localhost [127.0.0.1]) by freefall.freebsd.org (8.14.4/8.14.4) with ESMTP id oAB2o97x019923 for ; Thu, 11 Nov 2010 02:50:09 GMT (envelope-from gnats@freefall.freebsd.org) Received: (from gnats@localhost) by freefall.freebsd.org (8.14.4/8.14.4/Submit) id oAB2o8hE019922; Thu, 11 Nov 2010 02:50:09 GMT (envelope-from gnats) Date: Thu, 11 Nov 2010 02:50:09 GMT Message-Id: <201011110250.oAB2o8hE019922@freefall.freebsd.org> To: freebsd-ppc@FreeBSD.org From: dfilter@FreeBSD.ORG (dfilter service) Cc: Subject: Re: powerpc/111296: commit references a PR X-BeenThere: freebsd-ppc@freebsd.org X-Mailman-Version: 2.1.5 Precedence: list Reply-To: dfilter service List-Id: Porting FreeBSD to the PowerPC List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , X-List-Received-Date: Thu, 11 Nov 2010 02:50:09 -0000 The following reply was made to PR powerpc/111296; it has been noted by GNATS. From: dfilter@FreeBSD.ORG (dfilter service) To: bug-followup@FreeBSD.org Cc: Subject: Re: powerpc/111296: commit references a PR Date: Thu, 11 Nov 2010 02:40:16 +0000 (UTC) Author: nwhitehorn Date: Thu Nov 11 02:40:00 2010 New Revision: 215107 URL: http://svn.freebsd.org/changeset/base/215107 Log: Add support for the IMISS, DLMISS, and DSMISS traps required to run FreeBSD on a G2 core. PR: powerpc/111296 Submitted by: Andrew Turner Modified: head/sys/powerpc/aim/machdep.c head/sys/powerpc/aim/trap_subr32.S Modified: head/sys/powerpc/aim/machdep.c ============================================================================== --- head/sys/powerpc/aim/machdep.c Thu Nov 11 02:37:50 2010 (r215106) +++ head/sys/powerpc/aim/machdep.c Thu Nov 11 02:40:00 2010 (r215107) @@ -245,6 +245,9 @@ extern void *dsitrap, *dsisize; extern void *decrint, *decrsize; extern void *extint, *extsize; extern void *dblow, *dbsize; +extern void *imisstrap, *imisssize; +extern void *dlmisstrap, *dlmisssize; +extern void *dsmisstrap, *dsmisssize; uintptr_t powerpc_init(vm_offset_t startkernel, vm_offset_t endkernel, @@ -491,6 +494,12 @@ powerpc_init(vm_offset_t startkernel, vm bcopy(generictrap, (void *)EXC_VEC, (size_t)&trapsize); bcopy(generictrap, (void *)EXC_VECAST_G4, (size_t)&trapsize); bcopy(generictrap, (void *)EXC_VECAST_G5, (size_t)&trapsize); + #ifndef __powerpc64__ + /* G2-specific TLB miss helper handlers */ + bcopy(&imisstrap, (void *)EXC_IMISS, (size_t)&imisssize); + bcopy(&dlmisstrap, (void *)EXC_DLMISS, (size_t)&dlmisssize); + bcopy(&dsmisstrap, (void *)EXC_DSMISS, (size_t)&dsmisssize); + #endif __syncicache(EXC_RSVD, EXC_LAST - EXC_RSVD); /* Modified: head/sys/powerpc/aim/trap_subr32.S ============================================================================== --- head/sys/powerpc/aim/trap_subr32.S Thu Nov 11 02:37:50 2010 (r215106) +++ head/sys/powerpc/aim/trap_subr32.S Thu Nov 11 02:40:00 2010 (r215107) @@ -362,6 +362,207 @@ CNAME(alitrap): CNAME(alisize) = .-CNAME(alitrap) /* + * G2 specific: instuction TLB miss. + */ + .globl CNAME(imisstrap),CNAME(imisssize) +CNAME(imisstrap): + mfspr %r2, SPR_HASH1 /* get first pointer */ + addi %r1, 0, 8 /* load 8 for counter */ + mfctr %r0 /* save counter */ + mfspr %r3, SPR_ICMP /* get first compare value */ + addi %r2, %r2, -8 /* pre dec the pointer */ +im0: + mtctr %r1 /* load counter */ +im1: + lwzu %r1, 8(%r2) /* get next pte */ + cmp 0, %r1, %r3 /* see if found pte */ + bdnzf 2, im1 /* dec count br if cmp ne and if + * count not zero */ + bne instr_sec_hash /* if not found set up second hash + * or exit */ + lwz %r1, +4(%r2) /* load tlb entry lower-word */ + andi. %r3, %r1, 8 /* check G bit */ + bne do_isi_prot /* if guarded, take an ISI */ + mtctr %r0 /* restore counter */ + mfspr %r0, SPR_IMISS /* get the miss address for the tlbli */ + mfspr %r3, SPR_SRR1 /* get the saved cr0 bits */ + mtcrf 0x80, %r3 /* restore CR0 */ + mtspr SPR_RPA, %r1 /* set the pte */ + ori %r1, %r1, 0x100 /* set reference bit */ + srwi %r1, %r1, 8 /* get byte 7 of pte */ + tlbli %r0 /* load the itlb */ + stb %r1, +6(%r2) /* update page table */ + rfi /* return to executing program */ + +instr_sec_hash: + andi. %r1, %r3, 0x0040 /* see if we have done second hash */ + bne do_isi /* if so, go to ISI interrupt */ + mfspr %r2, SPR_HASH2 /* get the second pointer */ + ori %r3, %r3, 0x0040 /* change the compare value */ + addi %r1, %r0, 8 /* load 8 for counter */ + addi %r2, %r2, -8 /* pre dec for update on load */ + b im0 /* try second hash */ + +/* Create a faked ISI interrupt as the address was not found */ +do_isi_prot: + mfspr %r3, SPR_SRR1 /* get srr1 */ + andi. %r2, %r3, 0xffff /* clean upper srr1 */ + addis %r2, %r2, 0x0800 /* or in srr<4> = 1 to flag prot + * violation */ + b isi1 +do_isi: + mfspr %r3, SPR_SRR1 /* get srr1 */ + andi. %r2, %r3, 0xffff /* clean srr1 */ + addis %r2, %r2, 0x4000 /* or in srr1<1> = 1 to flag pte + * not found */ +isi1: + mtctr %r0 /* restore counter */ + mtspr SPR_SRR1, %r2 /* set srr1 */ + mfmsr %r0 /* get msr */ + xoris %r0, %r0, 0x2 /* flip the msr bit */ + mtcrf 0x80, %r3 /* restore CR0 */ + mtmsr %r0 /* flip back to the native gprs */ + ba EXC_ISI /* go to instr. access interrupt */ + +CNAME(imisssize) = .-CNAME(imisstrap) + +/* + * G2 specific: data load TLB miss. + */ + .globl CNAME(dlmisstrap),CNAME(dlmisssize) +CNAME(dlmisstrap): + mfspr %r2, SPR_HASH1 /* get first pointer */ + addi %r1, 0, 8 /* load 8 for counter */ + mfctr %r0 /* save counter */ + mfspr %r3, SPR_DCMP /* get first compare value */ + addi %r2, %r2, -8 /* pre dec the pointer */ +dm0: + mtctr %r1 /* load counter */ +dm1: + lwzu %r1, 8(%r2) /* get next pte */ + cmp 0, 0, %r1, %r3 /* see if found pte */ + bdnzf 2, dm1 /* dec count br if cmp ne and if + * count not zero */ + bne data_sec_hash /* if not found set up second hash + * or exit */ + lwz %r1, +4(%r2) /* load tlb entry lower-word */ + mtctr %r0 /* restore counter */ + mfspr %r0, SPR_DMISS /* get the miss address for the tlbld */ + mfspr %r3, SPR_SRR1 /* get the saved cr0 bits */ + mtcrf 0x80, %r3 /* restore CR0 */ + mtspr SPR_RPA, %r1 /* set the pte */ + ori %r1, %r1, 0x100 /* set reference bit */ + srwi %r1, %r1, 8 /* get byte 7 of pte */ + tlbld %r0 /* load the dtlb */ + stb %r1, +6(%r2) /* update page table */ + rfi /* return to executing program */ + +data_sec_hash: + andi. %r1, %r3, 0x0040 /* see if we have done second hash */ + bne do_dsi /* if so, go to DSI interrupt */ + mfspr %r2, SPR_HASH2 /* get the second pointer */ + ori %r3, %r3, 0x0040 /* change the compare value */ + addi %r1, 0, 8 /* load 8 for counter */ + addi %r2, %r2, -8 /* pre dec for update on load */ + b dm0 /* try second hash */ + +CNAME(dlmisssize) = .-CNAME(dlmisstrap) + +/* + * G2 specific: data store TLB miss. + */ + .globl CNAME(dsmisstrap),CNAME(dsmisssize) +CNAME(dsmisstrap): + mfspr %r2, SPR_HASH1 /* get first pointer */ + addi %r1, 0, 8 /* load 8 for counter */ + mfctr %r0 /* save counter */ + mfspr %r3, SPR_DCMP /* get first compare value */ + addi %r2, %r2, -8 /* pre dec the pointer */ +ds0: + mtctr %r1 /* load counter */ +ds1: + lwzu %r1, 8(%r2) /* get next pte */ + cmp 0, 0, %r1, %r3 /* see if found pte */ + bdnzf 2, ds1 /* dec count br if cmp ne and if + * count not zero */ + bne data_store_sec_hash /* if not found set up second hash + * or exit */ + lwz %r1, +4(%r2) /* load tlb entry lower-word */ + andi. %r3, %r1, 0x80 /* check the C-bit */ + beq data_store_chk_prot /* if (C==0) + * go check protection modes */ +ds2: + mtctr %r0 /* restore counter */ + mfspr %r0, SPR_DMISS /* get the miss address for the tlbld */ + mfspr %r3, SPR_SRR1 /* get the saved cr0 bits */ + mtcrf 0x80, %r3 /* restore CR0 */ + mtspr SPR_RPA, %r1 /* set the pte */ + tlbld %r0 /* load the dtlb */ + rfi /* return to executing program */ + +data_store_sec_hash: + andi. %r1, %r3, 0x0040 /* see if we have done second hash */ + bne do_dsi /* if so, go to DSI interrupt */ + mfspr %r2, SPR_HASH2 /* get the second pointer */ + ori %r3, %r3, 0x0040 /* change the compare value */ + addi %r1, 0, 8 /* load 8 for counter */ + addi %r2, %r2, -8 /* pre dec for update on load */ + b ds0 /* try second hash */ + +/* Check the protection before setting PTE(c-bit) */ +data_store_chk_prot: + rlwinm. %r3,%r1,30,0,1 /* test PP */ + bge- chk0 /* if (PP == 00 or PP == 01) + * goto chk0: */ + andi. %r3, %r1, 1 /* test PP[0] */ + beq+ chk2 /* return if PP[0] == 0 */ + b do_dsi_prot /* else DSIp */ +chk0: + mfspr %r3,SPR_SRR1 /* get old msr */ + andis. %r3,%r3,0x0008 /* test the KEY bit (SRR1-bit 12) */ + beq chk2 /* if (KEY==0) goto chk2: */ + b do_dsi_prot /* else do_dsi_prot */ +chk2: + ori %r1, %r1, 0x180 /* set reference and change bit */ + sth %r1, 6(%r2) /* update page table */ + b ds2 /* and back we go */ + +/* Create a faked DSI interrupt as the address was not found */ +do_dsi: + mfspr %r3, SPR_SRR1 /* get srr1 */ + rlwinm %r1,%r3,9,6,6 /* get srr1 to bit 6 for + * load/store, zero rest */ + addis %r1, %r1, 0x4000 /* or in dsisr<1> = 1 to flag pte + * not found */ + b dsi1 + +do_dsi_prot: + mfspr %r3, SPR_SRR1 /* get srr1 */ + rlwinm %r1,%r3,9,6,6 /* get srr1 to bit 6 for + *load/store, zero rest */ + addis %r1, %r1, 0x0800 /* or in dsisr<4> = 1 to flag prot + * violation */ + +dsi1: + mtctr %r0 /* restore counter */ + andi. %r2, %r3, 0xffff /* clear upper bits of srr1 */ + mtspr SPR_SRR1, %r2 /* set srr1 */ + mtspr SPR_DSISR, %r1 /* load the dsisr */ + mfspr %r1, SPR_DMISS /* get miss address */ + rlwinm. %r2,%r2,0,31,31 /* test LE bit */ + beq dsi2 /* if little endian then: */ + xor %r1, %r1, 0x07 /* de-mung the data address */ +dsi2: + mtspr SPR_DAR, %r1 /* put in dar */ + mfmsr %r0 /* get msr */ + xoris %r0, %r0, 0x2 /* flip the msr bit */ + mtcrf 0x80, %r3 /* restore CR0 */ + mtmsr %r0 /* flip back to the native gprs */ + ba EXC_DSI /* branch to DSI interrupt */ + +CNAME(dsmisssize) = .-CNAME(dsmisstrap) + +/* * Similar to the above for DSI * Has to handle BAT spills * and standard pagetable spills _______________________________________________ svn-src-all@freebsd.org mailing list http://lists.freebsd.org/mailman/listinfo/svn-src-all To unsubscribe, send any mail to "svn-src-all-unsubscribe@freebsd.org"