summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--sys/arch/macppc/include/powerpc.h9
-rw-r--r--sys/arch/macppc/macppc/autoconf.c57
-rw-r--r--sys/arch/macppc/macppc/clock.c3
-rw-r--r--sys/arch/macppc/macppc/machdep.c161
-rw-r--r--sys/arch/powerpc/include/pmap.h3
-rw-r--r--sys/arch/powerpc/powerpc/pmap.c10
6 files changed, 186 insertions, 57 deletions
diff --git a/sys/arch/macppc/include/powerpc.h b/sys/arch/macppc/include/powerpc.h
index 4a34f0cd251..64dca7da010 100644
--- a/sys/arch/macppc/include/powerpc.h
+++ b/sys/arch/macppc/include/powerpc.h
@@ -1,4 +1,4 @@
-/* $OpenBSD: powerpc.h,v 1.6 2002/09/15 09:01:58 deraadt Exp $ */
+/* $OpenBSD: powerpc.h,v 1.7 2005/10/09 14:01:11 drahn Exp $ */
/* $NetBSD: powerpc.h,v 1.1 1996/09/30 16:34:30 ws Exp $ */
/*
@@ -82,4 +82,11 @@ void install_extint(void (*handler) (void));
void ppc_intr_enable(int enable);
int ppc_intr_disable(void);
+struct dumpmem {
+ vaddr_t start;
+ vm_size_t end;
+};
+extern struct dumpmem dumpmem[VM_PHYSSEG_MAX];
+extern u_int ndumpmem;
+extern vaddr_t dumpspace;
#endif /* _MACHINE_POWERPC_H_ */
diff --git a/sys/arch/macppc/macppc/autoconf.c b/sys/arch/macppc/macppc/autoconf.c
index f6650b37e2f..262565bcecf 100644
--- a/sys/arch/macppc/macppc/autoconf.c
+++ b/sys/arch/macppc/macppc/autoconf.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: autoconf.c,v 1.16 2005/04/21 00:15:42 deraadt Exp $ */
+/* $OpenBSD: autoconf.c,v 1.17 2005/10/09 14:01:11 drahn Exp $ */
/*
* Copyright (c) 1996, 1997 Per Fogelstrom
* Copyright (c) 1995 Theo de Raadt
@@ -37,7 +37,7 @@
* from: Utah Hdr: autoconf.c 1.31 91/01/21
*
* from: @(#)autoconf.c 8.1 (Berkeley) 6/10/93
- * $Id: autoconf.c,v 1.16 2005/04/21 00:15:42 deraadt Exp $
+ * $Id: autoconf.c,v 1.17 2005/10/09 14:01:11 drahn Exp $
*/
/*
@@ -58,11 +58,12 @@
#include <dev/cons.h>
#include <uvm/uvm_extern.h>
#include <machine/autoconf.h>
+#include <machine/powerpc.h>
struct device *parsedisk(char *, int, int, dev_t *);
void setroot(void);
void swapconf(void);
-extern void dumpconf(void);
+void dumpconf(void);
int findblkmajor(struct device *);
char *findblkname(int);
static struct device * getdisk(char *, int, int, dev_t *);
@@ -81,6 +82,9 @@ int cold = 1; /* if 1, still working on cold-start */
char bootdev[16]; /* to hold boot dev name */
struct device *bootdv = NULL;
+struct dumpmem dumpmem[VM_PHYSSEG_MAX];
+u_int ndumpmem;
+
/*
* Configure all devices found that we know about.
* This is done at boot time.
@@ -125,9 +129,7 @@ diskconf()
#endif
setroot();
swapconf();
-#if 0
dumpconf();
-#endif
}
/*
@@ -149,56 +151,11 @@ swapconf()
swp->sw_nblks = ctod(dtoc(swp->sw_nblks));
}
}
-#if 0
- dumpconf();
-#endif
}
/*
* Crash dump handling.
*/
-u_long dumpmag = 0x8fca0101; /* magic number */
-int dumpsize = 0; /* size of dump in pages */
-long dumplo = -1; /* blocks */
-
-/*
- * This is called by configure to set dumplo and dumpsize.
- * Dumps always skip the first CLBYTES of disk space
- * in case there might be a disk label stored there.
- * If there is extra space, put dump at the end to
- * reduce the chance that swapping trashes it.
- */
-#if 0
-void
-dumpconf()
-{
- int nblks; /* size of dump area */
- int maj;
-
- if (dumpdev == NODEV)
- return;
- maj = major(dumpdev);
- if (maj < 0 || maj >= nblkdev)
- panic("dumpconf: bad dumpdev=0x%x", dumpdev);
- if (bdevsw[maj].d_psize == NULL)
- return;
- nblks = (*bdevsw[maj].d_psize)(dumpdev);
- if (nblks <= ctod(1))
- return;
-
- dumpsize = btoc(IOM_END + ctob(dumpmem_high));
-
- /* Always skip the first CLBYTES, in case there is a label there. */
- if (dumplo < ctod(1))
- dumplo = ctod(1);
-
- /* Put dump at end of partition, and make it fit. */
- if (dumpsize > dtoc(nblks - dumplo))
- dumpsize = dtoc(nblks - dumplo);
- if (dumplo < nblks - ctod(dumpsize))
- dumplo = nblks - ctod(dumpsize);
-}
-#endif
static struct nam2blk {
char *name;
diff --git a/sys/arch/macppc/macppc/clock.c b/sys/arch/macppc/macppc/clock.c
index c71737311d7..d934478ea54 100644
--- a/sys/arch/macppc/macppc/clock.c
+++ b/sys/arch/macppc/macppc/clock.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: clock.c,v 1.14 2004/06/28 02:49:10 aaron Exp $ */
+/* $OpenBSD: clock.c,v 1.15 2005/10/09 14:01:11 drahn Exp $ */
/* $NetBSD: clock.c,v 1.1 1996/09/30 16:34:40 ws Exp $ */
/*
@@ -40,6 +40,7 @@
#include <machine/autoconf.h>
#include <machine/pio.h>
#include <machine/intr.h>
+#include <machine/vmparam.h>
#include <machine/powerpc.h>
#include <dev/ofw/openfirm.h>
diff --git a/sys/arch/macppc/macppc/machdep.c b/sys/arch/macppc/macppc/machdep.c
index 09ccd65f14d..fe1ec99a0bc 100644
--- a/sys/arch/macppc/macppc/machdep.c
+++ b/sys/arch/macppc/macppc/machdep.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: machdep.c,v 1.74 2005/10/03 04:47:30 drahn Exp $ */
+/* $OpenBSD: machdep.c,v 1.75 2005/10/09 14:01:11 drahn Exp $ */
/* $NetBSD: machdep.c,v 1.4 1996/10/16 19:33:11 ws Exp $ */
/*
@@ -48,6 +48,9 @@
#include <sys/extent.h>
#include <sys/systm.h>
#include <sys/user.h>
+#include <sys/conf.h>
+#include <sys/core.h>
+#include <sys/kcore.h>
#include <uvm/uvm_extern.h>
@@ -776,10 +779,164 @@ cpu_sysctl(int *name, u_int namelen, void *oldp, size_t *oldlenp, void *newp,
}
}
+
+u_long dumpmag = 0x04959fca; /* magic number */
+int dumpsize = 0; /* size of dump in pages */
+long dumplo = -1; /* blocks */
+
+/*
+ * This is called by configure to set dumplo and dumpsize.
+ * Dumps always skip the first CLBYTES of disk space
+ * in case there might be a disk label stored there.
+ * If there is extra space, put dump at the end to
+ * reduce the chance that swapping trashes it.
+ */
+void dumpconf(void);
+void
+dumpconf()
+{
+ int nblks; /* size of dump area */
+ int maj;
+ int i;
+
+
+ if (dumpdev == NODEV)
+ return;
+ maj = major(dumpdev);
+ if (maj < 0 || maj >= nblkdev)
+ panic("dumpconf: bad dumpdev=0x%x", dumpdev);
+ if (bdevsw[maj].d_psize == NULL)
+ return;
+ nblks = (*bdevsw[maj].d_psize)(dumpdev);
+ if (nblks <= ctod(1))
+ return;
+
+ /* Always skip the first block, in case there is a label there. */
+
+ if (dumplo < ctod(1))
+ dumplo = ctod(1);
+
+ for (i = 0; i < ndumpmem; i++)
+ dumpsize = max(dumpsize, dumpmem[i].end);
+
+ /* Put dump at end of partition, and make it fit. */
+ if (dumpsize > dtoc(nblks - dumplo - 1))
+ dumpsize = dtoc(nblks - dumplo - 1);
+ if (dumplo < nblks - ctod(dumpsize) - 1)
+ dumplo = nblks - ctod(dumpsize) - 1;
+
+}
+
+#define BYTES_PER_DUMP (PAGE_SIZE) /* must be a multiple of pagesize */
+vaddr_t dumpspace;
+
+int
+reserve_dumppages(caddr_t p)
+{
+ dumpspace = (vaddr_t)p;
+ return BYTES_PER_DUMP;
+}
+
+/*
+ * cpu_dump: dump machine-dependent kernel core dump headers.
+ */
+int cpu_dump(void);
+int
+cpu_dump()
+{
+ int (*dump) (dev_t, daddr_t, caddr_t, size_t);
+ long buf[dbtob(1) / sizeof (long)];
+ kcore_seg_t *segp;
+
+ dump = bdevsw[major(dumpdev)].d_dump;
+
+ segp = (kcore_seg_t *)buf;
+
+ /*
+ * Generate a segment header.
+ */
+ CORE_SETMAGIC(*segp, KCORE_MAGIC, MID_MACHINE, CORE_CPU);
+ segp->c_size = dbtob(1) - ALIGN(sizeof(*segp));
+
+ return (dump(dumpdev, dumplo, (caddr_t)buf, dbtob(1)));
+}
+
void
dumpsys()
{
- printf("dumpsys: TBD\n");
+#if 0
+ u_int npg;
+ u_int i, j;
+ daddr_t blkno;
+ int (*dump) (dev_t, daddr_t, caddr_t, size_t);
+ char *str;
+ int maddr;
+ extern int msgbufmapped;
+ int error;
+
+ /* save registers */
+
+ msgbufmapped = 0; /* don't record dump msgs in msgbuf */
+ if (dumpdev == NODEV)
+ return;
+ /*
+ * For dumps during autoconfiguration,
+ * if dump device has already configured...
+ */
+ if (dumpsize == 0)
+ dumpconf();
+ if (dumplo < 0)
+ return;
+ printf("dumping to dev %x, offset %ld\n", dumpdev, dumplo);
+
+ error = (*bdevsw[major(dumpdev)].d_psize)(dumpdev);
+ if (error == -1) {
+ printf("area unavailable\n");
+ delay (10000000);
+ return;
+ }
+
+ dump = bdevsw[major(dumpdev)].d_dump;
+ error = cpu_dump();
+ for (i = 0; !error && i < ndumpmem; i++) {
+ npg = dumpmem[i].end - dumpmem[i].start;
+ maddr = ctob(dumpmem[i].start);
+ blkno = dumplo + btodb(maddr) + 1;
+
+ for (j = npg; j;
+ j--, maddr += PAGE_SIZE, blkno+= btodb(PAGE_SIZE))
+ {
+ /* Print out how many MBs we have to go. */
+ if (dbtob(blkno - dumplo) % (1024 * 1024) < NBPG)
+ printf("%d ",
+ (ctob(dumpsize) - maddr) / (1024 * 1024));
+
+ pmap_enter(pmap_kernel(), dumpspace, maddr,
+ VM_PROT_READ, PMAP_WIRED);
+ if ((error = (*dump)(dumpdev, blkno,
+ (caddr_t)dumpspace, PAGE_SIZE)) != 0)
+ break;
+ }
+ }
+
+ switch (error) {
+
+ case 0: str = "succeeded\n\n"; break;
+ case ENXIO: str = "device bad\n\n"; break;
+ case EFAULT: str = "device not ready\n\n"; break;
+ case EINVAL: str = "area improper\n\n"; break;
+ case EIO: str = "i/o error\n\n"; break;
+ case EINTR: str = "aborted from console\n\n"; break;
+ default: str = "error %d\n\n"; break;
+ }
+ printf(str, error);
+
+#else
+ printf("dumpsys() - no yet supported\n");
+
+#endif
+ delay(5000000); /* 5 seconds */
+
}
volatile int cpl, ipending, astpending;
diff --git a/sys/arch/powerpc/include/pmap.h b/sys/arch/powerpc/include/pmap.h
index 039b320cbbf..dafc5d78490 100644
--- a/sys/arch/powerpc/include/pmap.h
+++ b/sys/arch/powerpc/include/pmap.h
@@ -1,4 +1,4 @@
-/* $OpenBSD: pmap.h,v 1.39 2005/10/03 02:18:50 drahn Exp $ */
+/* $OpenBSD: pmap.h,v 1.40 2005/10/09 14:01:11 drahn Exp $ */
/* $NetBSD: pmap.h,v 1.1 1996/09/30 16:34:29 ws Exp $ */
/*-
@@ -134,6 +134,7 @@ void switchexit(struct proc *);
int pte_spill_v(struct pmap *pm, u_int32_t va, u_int32_t dsisr, int exec_fault);
#define pmap_copy(dst_pmap, src_pmap, dst_addr, len, src_addr) ;
+int reserve_dumppages(caddr_t p);
void pmap_proc_iflush(struct proc *proc, vaddr_t va, vsize_t len);
#define pmap_unuse_final(p) /* nothing */
diff --git a/sys/arch/powerpc/powerpc/pmap.c b/sys/arch/powerpc/powerpc/pmap.c
index 68dcb6eefd5..2e61469ae1b 100644
--- a/sys/arch/powerpc/powerpc/pmap.c
+++ b/sys/arch/powerpc/powerpc/pmap.c
@@ -1,4 +1,4 @@
-/* $OpenBSD: pmap.c,v 1.92 2005/10/08 06:03:00 drahn Exp $ */
+/* $OpenBSD: pmap.c,v 1.93 2005/10/09 14:01:11 drahn Exp $ */
/*
* Copyright (c) 2001, 2002 Dale Rahn.
@@ -1319,8 +1319,12 @@ pmap_avail_setup(void)
pmap_cnt_avail = 0;
physmem = 0;
- for (mp = pmap_mem; mp->size !=0; mp++)
+ ndumpmem = 0;
+ for (mp = pmap_mem; mp->size !=0; mp++, ndumpmem++) {
physmem += btoc(mp->size);
+ dumpmem[ndumpmem].start = atop(mp->start);
+ dumpmem[ndumpmem].end = atop(mp->start + mp->size);
+ }
for (mp = pmap_avail; mp->size !=0 ; mp++) {
if (physmaxaddr < mp->start + mp->size)
@@ -1565,6 +1569,8 @@ pmap_bootstrap(u_int kernelstart, u_int kernelend)
ppc_kvm_stolen += PAGE_SIZE;
copy_dst_page = VM_MIN_KERNEL_ADDRESS + ppc_kvm_stolen;
ppc_kvm_stolen += PAGE_SIZE;
+ ppc_kvm_stolen += reserve_dumppages( (caddr_t)(VM_MIN_KERNEL_ADDRESS +
+ ppc_kvm_stolen));
/*