Port-powerpc archive
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]
Re: 20020313+0314 time warp version works on kbd/screen
For the folks on port-powerpc, there is a change to
lib/libkern/arch/powerpc around 3/13 that broke booting on some powermacs
under certain circumstances.
On Sat, 15 Jun 2002, Makoto Fujiwara wrote:
> Bill> Can someone try Manuel's time warp, with most of the kernel at 3/14
> Bill> source, but lib/libkern/arch/powerpc at 3/13? The author of this change
> Bill> says it *should* compile.
>
> I did that. The kernel compiled works fine with kbd/screen.
Ok. We're making progress.
I've attached the diffs I find in cvs covering these files in this time
frame. Makoto, do you agree that these are the relevant diffs?
These diffs touch two files, sys/lib/libkern/arch/powerpc/bzero.S and
sys/lib/libkern/arch/powerpc/syncicache.c.
I believe we need only look at the KERNEL case code.
One weird thing about this change is that you need version 1.3 of
sys/arch/powerpc/mpc6xx/genassym.cf for it to work right. CPU_CI, used on
line 206 of bzero.S, isn't defined w/o the above file. I'm not sure why
bzero.S would compile.
The only other thing I can think of is that we're calling one of these
routines before the cache info has gotten filled in.
Try applying the diffs one at a time & see what's the problem.
Thanks!
Take care,
Bill
Index: syssrc/sys/lib/libkern/arch/powerpc/bzero.S
diff -u syssrc/sys/lib/libkern/arch/powerpc/bzero.S:1.2
syssrc/sys/lib/libkern/arch/powerpc/bzero.S:1.3
--- syssrc/sys/lib/libkern/arch/powerpc/bzero.S:1.2 Fri Nov 30 04:25:50 2001
+++ syssrc/sys/lib/libkern/arch/powerpc/bzero.S Wed Mar 13 02:59:29 2002
@@ -1,4 +1,4 @@
-/* $NetBSD: bzero.S,v 1.2 2001/11/30 02:25:50 mjl Exp $ */
+/* $NetBSD: bzero.S,v 1.3 2002/03/13 00:59:29 eeh Exp $ */
/*-
* Copyright (C) 2001 Martin J. Laubach <mjl%netbsd.org@localhost>
@@ -72,18 +72,19 @@
bl _GLOBAL_OFFSET_TABLE_@local-4
mflr r10
mtlr r9
- lwz r5,cache_size@got(r10)
+ lwz r5,cache_info@got(r10)
#else
- lis r5,cache_size@h
- ori r5,r5,cache_size@l
+ lis r5,cache_info@h
+ ori r5,r5,cache_info@l
#endif
- lwz r6, 0(r5)
+ lwz r6, 4(r5)
cmpwi r6, -1
bne+ cb_cacheline_known
/*----------------------------------------------------------------------*/
#define CTL_MACHDEP 7
#define CPU_CACHELINE 1
+#define CPU_CACHEINFO 5
#define STKFRAME_SZ 48
#define MIB 8
@@ -102,6 +103,29 @@
stw r4, R4_SAVE(r1)
stw r0, R0_SAVE(r1)
+
+
+ li r0, CTL_MACHDEP /* Construct MIB */
+ stw r0, MIB(r1)
+ li r0, CPU_CACHEINFO
+ stw r0, MIB+4(r1)
+
+ li r0, 4*4 /* Oldlenp := 4*4 */
+ stw r0, OLDPLEN(r1)
+
+ addi r3, r1, MIB
+ li r4, 2 /* namelen */
+ /* r5 already contains &cache_info */
+ addi r6, r1, OLDPLEN
+ li r7, 0
+ li r8, 0
+ bl PIC_PLT(_C_LABEL(sysctl))
+
+ cmpwi r3, 0 /* Check result */
+ beq 1f
+
+ /* Failure, try older sysctl */
+
li r0, CTL_MACHDEP /* Construct MIB */
stw r0, MIB(r1)
li r0, CPU_CACHELINE
@@ -112,12 +136,22 @@
addi r3, r1, MIB
li r4, 2 /* namelen */
- /* r5 already contains &cache_size */
+#ifdef PIC
+ mflr r9
+ bl _GLOBAL_OFFSET_TABLE_@local-4
+ mflr r10
+ mtlr r9
+ lwz r5,cache_info@got(r10)
+ addi r5, r5, 4
+#else
+ lis r5,cache_info+4@h
+ ori r5,r5,cache_info+4@l
+#endif
addi r6, r1, OLDPLEN
li r7, 0
li r8, 0
bl PIC_PLT(_C_LABEL(sysctl))
-
+1:
lwz r8, R8_SAVE(r1)
lwz r3, R3_SAVE(r1)
lwz r4, R4_SAVE(r1)
@@ -126,11 +160,11 @@
#ifdef PIC
bl _GLOBAL_OFFSET_TABLE_@local-4
mflr r10
- lwz r9, cache_size@got(r10)
- lwz r9, 0(r9)
+ lwz r9, cache_info@got(r10)
+ lwz r9, 4(r9)
#else
- lis r5, cache_size@ha
- lwz r9, cache_size@l(r5)
+ lis r5, cache_info+4@ha
+ lwz r9, cache_info+4@l(r5)
#endif
la r1, STKFRAME_SZ(r1)
lwz r5, 4(r1)
@@ -151,25 +185,28 @@
/* Okay, we know the cache line size (r9) and shift value (r10) */
cb_cacheline_known:
#ifdef PIC
- lwz r5, cache_size@got(r10)
- lwz r9, 0(r5)
+ lwz r5, cache_info@got(r10)
+ lwz r9, 4(r5)
lwz r5, cache_sh@got(r10)
lwz r10, 0(r5)
#else
- lis r9, cache_size@ha
- lwz r9, cache_size@l(r9)
+ lis r9, cache_info+4@ha
+ lwz r9, cache_info+4@l(r9)
lis r10, cache_sh@ha
lwz r10, cache_sh@l(r10)
#endif
#else /* _KERNEL */
- li r9, CACHELINESIZE
-#if CACHELINESIZE == 32
-#define CACHELINESHIFT 5
+#ifdef MULTIPROCESSOR
+ mfspr r10, 0 /* Get cpu_info pointer */
#else
-#error Define CACHELINESHIFT for your CACHELINESIZE
+ lis r10, cpu_info_store@ha
+ addi r10, r10, cpu_info_store@l
#endif
- li r10, CACHELINESHIFT
+ lwz r9, CPU_CI+4(r10) /* Load D$ line size */
+ cntlzw r10, r9 /* Calculate shift.. */
+ li r6, 31
+ subf r10, r10, r6
#endif /* _KERNEL */
/* Back in memory filling business */
@@ -328,7 +365,7 @@
/*----------------------------------------------------------------------*/
#ifndef _KERNEL
.data
-cache_size: .long -1
+cache_info: .long -1, -1, -1, -1
cache_sh: .long 0
#endif
Index: syssrc/sys/lib/libkern/arch/powerpc/syncicache.c
diff -u syssrc/sys/lib/libkern/arch/powerpc/syncicache.c:1.4
syssrc/sys/lib/libkern/arch/powerpc/syncicache.c:1.5
--- syssrc/sys/lib/libkern/arch/powerpc/syncicache.c:1.4 Thu Aug 23
00:19:58 2001
+++ syssrc/sys/lib/libkern/arch/powerpc/syncicache.c Wed Mar 13 02:59:29 2002
@@ -1,4 +1,4 @@
-/* $NetBSD: syncicache.c,v 1.4 2001/08/22 21:19:58 matt Exp $ */
+/* $NetBSD: syncicache.c,v 1.5 2002/03/13 00:59:29 eeh Exp $ */
/*
* Copyright (C) 1995-1997, 1999 Wolfgang Solfrank.
@@ -40,54 +40,89 @@
#include <machine/cpu.h>
-#if defined(_KERNEL) || defined(_STANDALONE)
+
+#if defined(_STANDALONE)
#ifndef CACHELINESIZE
#error "Must know the size of a cache line"
#endif
+static struct _cache_info {
+ CACHELINESIZE,
+ CACHELINESIZE,
+ CACHELINESIZE,
+ CACHELINESIZE
+};
+#define CACHEINFO _cache_info
+#elif defined(_KERNEL)
+#define CACHEINFO (curcpu()->ci_ci)
#else
-static void getcachelinesize __P((void));
+static void getcachelinesize (void);
-static int _cachelinesize;
-#define CACHELINESIZE _cachelinesize
+static int _cachelinesize = 0;
+static struct cache_info _cache_info;
+#define CACHEINFO _cache_info
+
static void
-getcachelinesize()
+getcachelinesize(void)
{
static int cachemib[] = { CTL_MACHDEP, CPU_CACHELINE };
- int clen = sizeof(_cachelinesize);
+ static int cacheinfomib[] = { CTL_MACHDEP, CPU_CACHEINFO };
+ size_t clen = sizeof(_cache_info);
+
+ if (sysctl(cacheinfomib, sizeof(cacheinfomib) / sizeof(cacheinfomib[0]),
+ &_cache_info, &clen, NULL, 0) == 0) {
+ _cachelinesize = _cache_info.dcache_line_size;
+ return;
+ }
+ /* Try older deprecated sysctl */
+ clen = sizeof(_cachelinesize);
if (sysctl(cachemib, sizeof(cachemib) / sizeof(cachemib[0]),
&_cachelinesize, &clen, NULL, 0) < 0
|| !_cachelinesize)
abort();
+
+ _cache_info.dcache_size = _cachelinesize;
+ _cache_info.dcache_line_size = _cachelinesize;
+ _cache_info.icache_size = _cachelinesize;
+ _cache_info.icache_line_size = _cachelinesize;
+ /* If there is no cache, indicate we have issued the sysctl. */
+ if (!_cachelinesize) _cachelinesize = 1;
}
#endif
void
-__syncicache(from, len)
- void *from;
- int len;
+__syncicache(void *from, int len)
{
int l, off;
char *p;
+ int linesz;
#if !defined(_KERNEL) && !defined(_STANDALONE)
if (!_cachelinesize)
getcachelinesize();
#endif
- off = (u_int)from & (CACHELINESIZE - 1);
- l = len += off;
- p = (char *)from - off;
- do {
- __asm__ __volatile ("dcbst 0,%0" :: "r"(p));
- p += CACHELINESIZE;
- } while ((l -= CACHELINESIZE) > 0);
+
+ if (CACHEINFO.dcache_size > 0) {
+ linesz = CACHEINFO.dcache_line_size;
+ off = (u_int)from & (linesz - 1);
+ l = len += off;
+ p = (char *)from - off;
+ do {
+ __asm__ __volatile ("dcbst 0,%0" :: "r"(p));
+ p += linesz;
+ } while ((l -= linesz) > 0);
+ }
__asm__ __volatile ("sync");
- p = (char *)from - off;
- do {
- __asm__ __volatile ("icbi 0,%0" :: "r"(p));
- p += CACHELINESIZE;
- } while ((len -= CACHELINESIZE) > 0);
- __asm__ __volatile ("sync"); /* required on 7450 */
+
+ if (CACHEINFO.icache_size > 0 ) {
+ linesz = CACHEINFO.icache_line_size;
+ off = (u_int)from & (linesz - 1);
+ p = (char *)from - off;
+ do {
+ __asm__ __volatile ("icbi 0,%0" :: "r"(p));
+ p += linesz;
+ } while ((len -= linesz) > 0);
+ }
__asm__ __volatile ("isync");
}
Home |
Main Index |
Thread Index |
Old Index