Since some people disapprove of white space cleanups mixed in regular commits
[coreboot.git] / src / cpu / amd / sc520 / raminit.c
index 79a7066cbb44b7f75a4f2eb789809e686beddbe9..e6232a8eb4aeaaeb83c414de83940221e392cbaf 100644 (file)
 
 #define OUTC(addr, val) *(unsigned char *)(addr) = (val)
 
+/* sadly, romcc can't quite handle what we want, so we do this ugly thing */
+#define drcctl   (( volatile unsigned char *)0xfffef010)
+#define drcmctl   (( volatile unsigned char *)0xfffef012)
+#define drccfg   (( volatile unsigned char *)0xfffef014)
 
-void
-setupsc520(void){
-       unsigned char *cp;
-       unsigned short *sp;
-       unsigned long *edi;
-       unsigned long *par;
+#define drcbendadr   (( volatile unsigned long *)0xfffef018)
+#define eccctl   (( volatile unsigned char *)0xfffef020)
+#define dbctl   (( volatile unsigned char *)0xfffef040)
+
+void setupsc520(void)
+{
+       volatile unsigned char *cp;
+       volatile unsigned short *sp;
+       volatile unsigned long *edi;
+
+       /* do this to see if MMCR will start acting right. we suspect
+        * you have to do SOMETHING to get things going. I'm really
+        * starting to hate this processor.
+        */
+
+       /* no, that did not help. I wonder what will?
+        * outl(0x800df0cb, 0xfffc);
+        */
+
+       /* well, this is special! You have to do SHORT writes to the
+        * locations, even though they are CHAR in size and CHAR aligned
+        * and technically, a SHORT write will result in -- yoo ha! --
+        * over writing the next location! Thanks to the u-boot guys
+        * for a reference code I can use. with these short pointers,
+        * it now reliably comes up after power cycle with printk. Ah yi
+        * yi.
+        */
 
        /* turn off the write buffer*/
-       cp = (unsigned char *)0xfffef040;
-       *cp = 0;
+       /* per the note above, make this a short? Let's try it. */
+       sp = (unsigned short *)0xfffef040;
+       *sp = 0;
 
+       /* as per the book: */
+       /* PAR register setup */
+       /* set up the PAR registers as they are on the MSM586SEG */
+       /*    moved to romstage.c by Stepan, Ron says: */
+       /* NOTE: move this to mainboard.c ASAP */
+       setup_pars();
+
+       /* CPCSF register */
+       sp =  (unsigned short *)0xfffefc24;
+       *sp = 0xfe;
+
+       /* ADDDECTL */
+       sp =  (unsigned short *)0xfffefc80;
+       *sp = 0x10;
+
+       /* byte writes in AMD assembly */
+       /* we do short anyway, since u-boot does ... */
        /*set the GP CS offset*/
-       cp =  (unsigned char *)0xfffefc08;
-       *cp = 0x00001;
+       sp =  (unsigned short *)0xfffefc08;
+       *sp = 0x00001;
        /*set the GP CS width*/
-       cp =  (unsigned char *)0xfffefc09;
-       *cp = 0x00003;
+       sp =  (unsigned short *)0xfffefc09;
+       *sp = 0x00003;
+
+       /* short writes in AMD assembly */
        /*set the GP CS width*/
-       cp =  (unsigned char *)0xfffefc0a;
-       *cp = 0x00001;
+       sp =  (unsigned short *)0xfffefc0a;
+       *sp = 0x00001;
        /*set the RD pulse width*/
-       cp =  (unsigned char *)0xfffefc0b;
-       *cp = 0x00003;
+       sp =  (unsigned short *)0xfffefc0b;
+       *sp = 0x00003;
        /*set the GP RD offset */
-       cp =  (unsigned char *)0xfffefc0c;
-       *cp = 0x00001;
+       sp =  (unsigned short *)0xfffefc0c;
+       *sp = 0x00001;
        /*set the GP WR pulse width*/
-       cp =  (unsigned char *)0xfffefc0d;
-       *cp = 0x00003;
+       sp =  (unsigned short *)0xfffefc0d;
+       *sp = 0x00003;
        /*set the GP WR offset*/
-       cp =  (unsigned char *)0xfffefc0e;
-       *cp = 0x00001;
+       sp =  (unsigned short *)0xfffefc0e;
+       *sp = 0x00001;
+
+
        /* set up the GP IO pins*/
        /*set the GPIO directionreg*/
        sp =  (unsigned short *)0xfffefc2c;
@@ -95,114 +142,60 @@ setupsc520(void){
        sp =  (unsigned short *)0xfffefc20;
        *sp = 0x0FFFF;
 
-#ifdef NETSC520
-if NetSC520
-; set the PIO regs correctly.
-       /*set the GPIO16-31 direction reg*/
-       sp =  (unsigned short *)0xfffefc2c;
-       *sp = 0x000ff;
-       /*set the PIODIR15_0 direction reg*/
-       sp =  (unsigned short *)0xfffefc2a;
-       *sp = 0x00440;
-       /*set the PIOPFS31_16 direction reg*/
-       sp =  (unsigned short *)0xfffefc22;
-       *sp = 0x00600;
-       /*set the PIOPFS15_0 direction reg*/
-       sp =  (unsigned short *)0xfffefc20;
-       *sp = 0x0FBBF;
-       /*set the PIODATA15_0 reg*/
-       sp =  (unsigned short *)0x0xfffefc30;
-       *sp = 0x0f000;
-       /*set the CSPFS reg*/
-       sp =  (unsigned short *)0xfffefc24;
-       *sp = 0x0000;
-
-; The NetSC520 uses PIOs 16-23 for LEDs instead of port 80
-; output a 1 to the leds
-       /*set the GPIO16-31 direction reg*/
-       sp =  (unsigned short *)0xfffefc32;
-       mov     al, not 1
-else
-#endif
 
-       /* setup for the CDP*/
-       /*set the GPIO directionreg*/
-       sp =  (unsigned short *)0xfffefc2c;
-       *sp = 0x00000;
-       /*set the GPIO directionreg*/
-       sp =  (unsigned short *)0xfffefc2a;
-       *sp = 0x00000;
-       /*set the GPIO pin function 31-16 reg*/
-       sp =  (unsigned short *)0xfffefc22;
-       *sp = 0x0FFFF;
-       /*set the GPIO pin function 15-0 reg*/
-       sp =  (unsigned short *)0xfffefc20;
-       *sp = 0x0FFFF;
        /* the 0x80 led should now be working*/
        outb(0xaa, 0x80);
-/*
-; set up a PAR to allow access to the 680 leds
-;      WriteMMCR( 0xc4,0x28000680);            // PAR15
- */
-/*; set the uart baud rate clocks to the normal 1.8432 MHz.*/
+#if 0
+       /* wtf are 680 leds ... */
+       par = (unsigned long *) 0xfffef0c4;
+       *par = 0x28000680;
+       /* well? */
+       outb(0x55, 0x80);
+#endif
+
+       /* set the uart baud rate clocks to the normal 1.8432 MHz.*/
+       /* enable interrupts here? Why not? */
        cp = (unsigned char *)0xfffefcc0;
-       *cp = 4;                                        /* uart 1 clock source */
+       *cp = 4 | 3;                    /* uart 1 clock source */
        cp = (unsigned char *)0xfffefcc4;
-       *cp = 4;                                        /* uart 2 clock source */
+       *cp = 4;                        /* uart 2 clock source */
+
+#if 0
 /*; set the interrupt mapping registers.*/
        cp = (unsigned char *)0x0fffefd20;
        *cp = 0x01;
-       
+
        cp = (unsigned char *)0x0fffefd28;
        *cp = 0x0c;
-       
+
        cp = (unsigned char *)0x0fffefd29;
        *cp = 0x0b;
-       
+
        cp = (unsigned char *)0x0fffefd30;
        *cp = 0x07;
-       
+
        cp = (unsigned char *)0x0fffefd43;
        *cp = 0x03;
-       
+
        cp = (unsigned char *)0x0fffefd51;
        *cp = 0x02;
-       
-/*; "enumerate" the PCI. Mainly set the interrupt bits on the PCnetFast. */
-       outl(0xcf8, 0x08000683c);
-       outl(0xcfc, 0xc); /* set the interrupt line */
-
-/*; Set the SC520 PCI host bridge to target mode to allow external*/
-/*; bus mastering events*/
-
-       outl(0x0cf8,0x080000004);       /*index the status command register on device 0*/
-       outl(0xcfc, 0x2);                       /*set the memory access enable bit*/
-       OUTC(0x0fffef072, 1);           /* enable req bits in SYSARBMENB */
-
-
+#endif
 
-       /* set up the PAR registers as they are on the MSM586SEG */
-       par = (unsigned long *) 0xfffef080;
-       *par++ = 0x607c00a0; /*PAR0: PCI:Base 0xa0000; size 0x1f000:*/
-       *par++ = 0x480400d8; /*PAR1: GP BUS MEM:CS2:Base 0xd8, size 0x4:*/
-       *par++ = 0x340100ea; /*PAR2: GP BUS IO:CS5:Base 0xea, size 0x1:*/
-       *par++ = 0x380701f0; /*PAR3: GP BUS IO:CS6:Base 0x1f0, size 0x7:*/
-       *par++ = 0x3c0003f6; /*PAR4: GP BUS IO:CS7:Base 0x3f6, size 0x0:*/
-       *par++ = 0x35ff0400; /*PAR5: GP BUS IO:CS5:Base 0x400, size 0xff:*/
-       *par++ = 0x35ff0600; /*PAR6: GP BUS IO:CS5:Base 0x600, size 0xff:*/
-       *par++ = 0x35ff0800; /*PAR7: GP BUS IO:CS5:Base 0x800, size 0xff:*/
-       *par++ = 0x35ff0a00; /*PAR8: GP BUS IO:CS5:Base 0xa00, size 0xff:*/
-       *par++ = 0x35ff0e00; /*PAR9: GP BUS IO:CS5:Base 0xe00, size 0xff:*/
-       *par++ = 0x34fb0104; /*PAR10: GP BUS IO:CS5:Base 0x104, size 0xfb:*/
-       *par++ = 0x35af0200; /*PAR11: GP BUS IO:CS5:Base 0x200, size 0xaf:*/
-       *par++ = 0x341f03e0; /*PAR12: GP BUS IO:CS5:Base 0x3e0, size 0x1f:*/
-       *par++ = 0xe41c00c0; /*PAR13: SDRAM:code:cache:nowrite:Base 0xc0000, size 0x7000:*/
-       *par++ = 0x545c00c8; /*PAR14: GP BUS MEM:CS5:Base 0xc8, size 0x5c:*/
-//     *par++ = 0x8a020200; /*PAR15: BOOTCS:code:nocache:write:Base 0x2000000, size 0x80000:*/
+/* Stepan says: This needs to go to the msm586seg code */
+/* "enumerate" the PCI. Mainly set the interrupt bits on the PCnetFast. */
+       outl(0x08000683c, 0xcf8);
+       outl(0xc, 0xcfc); /* set the interrupt line */
 
 
+       /* Set the SC520 PCI host bridge to target mode to
+        * allow external bus mastering events
+        */
+       /* index the status command register on device 0*/
+       outl(0x080000004, 0x0cf8);
+       outl(0x2, 0xcfc);               /*set the memory access enable bit*/
+       OUTC(0x0fffef072, 1);           /* enable req bits in SYSARBMENB */
 }
-       
+
 
 /*
  *
@@ -235,296 +228,192 @@ else
 #define ROW11_DATA 0x07070707  /*  11 row data/also bank switch (MASK)*/
 #define ROW10_DATA 0xaaaaaaaa  /*  10 row data/also bank switch (MASK)*/
 
-void 
+void
 dummy_write(void){
   volatile unsigned short *ptr = (volatile unsigned short *)CACHELINESZ;
   *ptr = 0;
 }
 
-void sc520_udelay(int microseconds) {
-       volatile int x;
-       for(x = 0; x < 1000; x++)
-               ;
-}
-
-struct ramctl {
-       unsigned char drcctl;
-       unsigned char pad1;
-       unsigned char drcmctl;
-       unsigned char pad2;
-       unsigned char drccfg;
-       unsigned char pad[3];
-  unsigned char drcbendadr[4];
-};
-
-#define RAMCTL (struct ramctl *) 0xfffef010
+#include "pc80/udelay_io.c"
 
 static void dumpram(void){
-  struct ramctl *ram = RAMCTL;
-  print_err("ctl "); print_err_hex8(ram->drcctl); print_err("\r\n");
-  print_err("mctl "); print_err_hex8(ram->drcmctl); print_err("\r\n");
-  print_err("cfg "); print_err_hex8(ram->drccfg); print_err("\r\n");
-
-  print_err("bendadr0 "); print_err_hex8(ram->drcbendadr[0]); print_err("\r\n");
-  print_err("bendadr1 "); print_err_hex8(ram->drcbendadr[1]); print_err("\r\n");
-  print_err("bendadr2 "); print_err_hex8(ram->drcbendadr[2]); print_err("\r\n");
-  print_err("bendadr3"); print_err_hex8(ram->drcbendadr[3]); print_err("\r\n");
+  print_err("ctl "); print_err_hex8(*drcctl); print_err("\n");
+  print_err("mctl "); print_err_hex8(*drcmctl); print_err("\n");
+  print_err("cfg "); print_err_hex8(*drccfg); print_err("\n");
+
+  print_err("bendadr0 "); print_err_hex8(*drcbendadr); print_err("\n");
+  print_err("bendadr1 "); print_err_hex8(*drcbendadr); print_err("\n");
+  print_err("bendadr2 "); print_err_hex8(*drcbendadr); print_err("\n");
+  print_err("bendadr3"); print_err_hex8(*drcbendadr); print_err("\n");
 }
 
-struct eccctl {
-       unsigned char eccctl;
-       unsigned char eccsta;
-       unsigned char eccckbpos;
-       unsigned char ecccktest;
-       unsigned char eccsbadd;
-       unsigned char pad[3];
-       unsigned char eccmbad;
-};
-
-#define ECCCTL (struct eccctl *) 0xfffef020
-
-#define DBCTL (unsigned char *) 0xfffef040
+/* there is a lot of silliness in the amd code, and it is
+ * causing romcc real headaches, so we're going to be be a little
+ * less silly.
+ * so, the order of ops is:
+ * for i in 3 to 0
+ * see if bank is there.
+ * if we can write a word, and read it back, to hell with paranoia
+ * the bank is there. So write the magic byte, read it back, and
+ * use that to get size, etc. Try to keep things very simple,
+ * so people can actually follow the damned code.
+ */
 
-#if 0
-int nextbank(int bank)
+/* cache is assumed to be disabled */
+int sizemem(void)
 {
-       struct ramctl *ram = RAMCTL;
-       struct eccctl *ecc = ECCCTL;
-       unsigned char *dbctl = DBCTL;
 
-       int rows,banks, cols, i;
-       unsigned char ending_adr;
+       int rows,banks, cols, i, bank;
+       unsigned char al;
+       volatile unsigned long *lp = (volatile unsigned long *) CACHELINESZ;
+       unsigned long l;
+       /* initialize dram controller registers */
+       /* disable write buffer/read-ahead buffer */
+       *dbctl = 0;
+       /* no ecc interrupts of any kind. */
+       *eccctl = 0;
+       /* Set SDRAM timing for slowest speed. */
+       *drcmctl = 0x1e;
 
-       /* this is really ugly, it is right from assembly code. 
-        * we need to clean it up later
+       /* setup dram register for all banks
+        * with max cols and max banks
+        * this is the oldest trick in the book. You are going to set up for max rows
+        * and cols, then do a write, then see if the data is wrapped to low memory.
+        * you can actually tell by which data gets to which low memory,
+        * exactly how many rows and cols you have.
         */
-       
-start:
-       /* write col 11 wrap adr */
-       COL11_ADR=COL11_DATA;
-       if(COL11_ADR!=COL11_DATA)
-               goto bad_ram;
-//while(1)
-print_err("11\n");
-       /* write col 10 wrap adr */
-       COL10_ADR=COL10_DATA;
-       if(COL10_ADR!=COL10_DATA)
-               goto bad_ram;
-print_err("10\n");
-
-       /* write col 9 wrap adr */
-       COL09_ADR=COL09_DATA;
-       if(COL09_ADR!=COL09_DATA)
-               goto bad_ram;
-print_err("9\n");
-
-       /* write col 8 wrap adr */
-       COL08_ADR=COL08_DATA;
-       if(COL08_ADR!=COL08_DATA)
-               goto bad_ram;
-print_err("8\n");
-
-       /* write row 14 wrap adr */
-       ROW14_ADR=ROW14_DATA;
-       if(ROW14_ADR!=ROW14_DATA)
-               goto bad_ram;
-print_err("14\n");
-
-       /* write row 13 wrap adr */
-       ROW13_ADR=ROW13_DATA;
-       if(ROW13_ADR!=ROW13_DATA)
-               goto bad_ram;
-print_err("13\n");
-
-       /* write row 12 wrap adr */
-       ROW12_ADR=ROW12_DATA;
-       if(ROW12_ADR!=ROW12_DATA)
-               goto bad_ram;
-print_err("12\n");
-
-       /* write row 11 wrap adr */
-       ROW11_ADR=ROW11_DATA;
-       if(ROW11_ADR!=ROW11_DATA)
-               goto bad_ram;
-print_err("11\n");
-
-       /* write row 10 wrap adr */
-       ROW10_ADR=ROW10_DATA;
-       if(ROW10_ADR!=ROW10_DATA)
-               goto bad_ram;
-print_err("10\n");
-
-/*
- * read data @ row 12 wrap adr to determine # banks,
- *  and read data @ row 14 wrap adr to determine # rows.
- *  if data @ row 12 wrap adr is not AA, 11 or 12 we have bad RAM.
- * if data @ row 12 wrap == AA, we only have 2 banks, NOT 4
- * if data @ row 12 wrap == 11 or 12, we have 4 banks
- */
+       *drccfg=0xbbbb;
 
-       banks=2;
-       if (ROW12_ADR != ROW10_DATA) {
-               banks=4;
-print_err("4b\n");
-               if(ROW12_ADR != ROW11_DATA) {
-                       if(ROW12_ADR != ROW12_DATA)
-                               goto bad_ram;
-               }
-       }
-
-       /* validate row mask */
-       rows=ROW14_ADR;
-       if (rows<ROW11_DATA)
-               goto bad_ram;
-       if (rows>ROW14_DATA)
-               goto bad_ram;
-       /* verify all 4 bytes of dword same */
-       if(rows&0xffff!=(rows>>16)&0xffff)
-               goto bad_ram;
-       if(rows&0xff!=(rows>>8)&0xff)
-               goto bad_ram;
-       
-       print_err("rows"); print_err_hex32(rows); print_err("\n");
-       /* validate column data */
-       cols=COL11_ADR;
-       if(cols<COL08_DATA)
-               goto bad_ram;
-       if (cols>COL11_DATA)
-               goto bad_ram;
-       /* verify all 4 bytes of dword same */
-       if(cols&0xffff!=(cols>>16)&0xffff)
-               goto bad_ram;
-       if(cols&0xff!=(cols>>8)&0xff)
-               goto bad_ram;
-       print_err("cols"); print_err_hex32(cols); print_err("\n");
-       cols -= COL08_DATA;
+       /* setup loop to do 4 external banks starting with bank 3 */
+       *drcbendadr=0x0ff000000;
+       /* for now, set it up for one loop of bank 0. Just to get it to go at all. */
+       *drcbendadr=0x0ff;
 
-       i = cols + rows;
+       /* issue a NOP to all DRAMs */
+       /* Setup DRAM control register with Disable refresh,
+        * disable write buffer Test Mode and NOP command select
+        */
+       *drcctl=0x01;
 
-       /* wacky end addr calculation */
-/*
-       al = 3;
-       al -= (i & 0xff);k
- */
+       /* dummy write for NOP to take effect */
+       dummy_write();
+       print_err("NOP\n");
+       /* 100? 200? */
+       udelay(100);
+       print_err("after udelay\n");
 
-       
-       if(banks==4)
-               i+=8; /* <-- i holds merged value */
-       
-       /* fix ending addr mask*/
-       /*FIXME*/
-       /* let's just go with this to start ... see if we can get ANYWHERE */
-       ending_adr=0xff;
+       /* issue all banks precharge */
+       *drcctl=0x02;
+       print_err("set *drcctl to 2 \n");
+       dummy_write();
+       print_err("PRE\n");
 
-bad_reint:
-       /* issue all banks recharge */
-       ram->drcctl=0x02;
+       /* issue 2 auto refreshes to all banks */
+       *drcctl=0x04;
        dummy_write();
+       print_err("AUTO1\n");
+       dummy_write();
+       print_err("AUTO2\n");
 
-       /* update ending address register */
-       ram->drcbendadr[bank] = ending_adr;
-       
-       /* update config register */
-       ram->drccfg = (banks = 4 ? 8 : 0) | cols & 3;
-       /* skip the rest for now */
-       bank = 0;
-//     *drccfg=*drccfg&YYY|ZZZZ;
+       /* issue LOAD MODE REGISTER command */
+       *drcctl=0x03;
+       dummy_write();
+       print_err("LOAD MODE REG\n");
 
-       if(bank!=0) {
-               bank--;
-               //*(&*drcbendadr+XXYYXX)=0xff;
-               goto start;
+       *drcctl=0x04;
+       for (i=0; i<8; i++) /* refresh 8 times */{
+               dummy_write();
+               print_err("dummy write\n");
        }
+       print_err("8 dummy writes\n");
 
        /* set control register to NORMAL mode */
-       ram->drcctl=0x00;
-       dummy_write();
-       return bank;
-       
-bad_ram:
-       print_info("bad ram!\r\n");
-}
-#endif
-/* cache is assumed to be disabled */
-int sizemem(void)
-{
-       struct ramctl *ram = RAMCTL;
-       struct eccctl *ecc = ECCCTL;
-       unsigned char *dbctl = DBCTL;
-       int rows,banks, cols, i, bank;
-       unsigned char ending_adr, al;
-
-       /* initialize dram controller registers */
+       *drcctl=0x00;
+       print_err("normal\n");
 
-       *dbctl = 0; /* disable write buffer/read-ahead buffer */
-       ecc->eccctl = 0;
-       ram->drcmctl = 0x1e; /* Set SDRAM timing for slowest speed. */
+       print_err("HI done normal\n");
 
-       /* setup loop to do 4 external banks starting with bank 3 */
        print_err("sizemem\n");
-
-       /* enable last bank and setup ending address 
+       for(bank = 3; bank >= 0; bank--) {
+         print_err("Try to assign to l\n");
+         *lp = 0xdeadbeef;
+         print_err("assigned l ... \n");
+         if (*lp != 0xdeadbeef) {
+           print_err(" no memory at bank ");
+           // print_err_hex8(bank);
+           //   print_err(" value "); print_err_hex32(*lp);
+           print_err("\n");
+           //      continue;
+         }
+         *drcctl = 2;
+         dummy_write();
+         *drccfg = *drccfg >> 4;
+         l = *drcbendadr;
+         l >>= 8;
+         *drcbendadr = l;
+         print_err("loop around\n");
+         *drcctl = 0;
+         dummy_write();
+       }
+#if 0
+       /* enable last bank and setup ending address
         * register for max ram in last bank
         */
-       ram->drcbendadr[3]=0x0ff000000;
+       *drcbendadr=0x0ff000000;
 
-       /* setup dram register for all banks
-        * with max cols and max banks
-        */
-       ram->drccfg=0xbbbb;
 
-       dumpram();
+//     dumpram();
 
        /* issue a NOP to all DRAMs */
        /* Setup DRAM control register with Disable refresh,
         * disable write buffer Test Mode and NOP command select
         */
-       ram->drcctl=0x01;
+       *drcctl=0x01;
 
        /* dummy write for NOP to take effect */
        dummy_write();
        print_err("NOP\n");
        /* 100? 200? */
-       //sc520_udelay(100);
-       print_err("after sc520_udelay\r\n");
+       //udelay(100);
+       print_err("after udelay\n");
 
        /* issue all banks precharge */
-       ram->drcctl=0x02;
-       print_err("set *drcctl to 2 \r\n");
+       *drcctl=0x02;
+       print_err("set *drcctl to 2 \n");
        dummy_write();
        print_err("PRE\n");
 
        /* issue 2 auto refreshes to all banks */
-       ram->drcctl=0x04;
+       *drcctl=0x04;
        dummy_write();
        print_err("AUTO1\n");
        dummy_write();
        print_err("AUTO2\n");
 
        /* issue LOAD MODE REGISTER command */
-       ram->drcctl=0x03;
+       *drcctl=0x03;
        dummy_write();
        print_err("LOAD MODE REG\n");
 
-       ram->drcctl=0x04;
+       *drcctl=0x04;
        for (i=0; i<8; i++) /* refresh 8 times */{
                dummy_write();
-               print_err("dummy write\r\n");
+               print_err("dummy write\n");
        }
        print_err("8 dummy writes\n");
 
        /* set control register to NORMAL mode */
-       ram->drcctl=0x00;
+       *drcctl=0x00;
        print_err("normal\n");
 
-       print_err("HI done normal\r\n");
+       print_err("HI done normal\n");
        bank = 3;
 
 
-       /* this is really ugly, it is right from assembly code. 
+       /* this is really ugly, it is right from assembly code.
         * we need to clean it up later
         */
-       
+
 start:
        /* write col 11 wrap adr */
        COL11_ADR=COL11_DATA;
@@ -605,11 +494,12 @@ print_err("4b\n");
        if (rows>ROW14_DATA)
                goto bad_ram;
        /* verify all 4 bytes of dword same */
+/*
        if(rows&0xffff!=(rows>>16)&0xffff)
                goto bad_ram;
        if(rows&0xff!=(rows>>8)&0xff)
                goto bad_ram;
-
+*/
        /* now just get one of them */
        rows &= 0xff;
        print_err("rows"); print_err_hex32(rows); print_err("\n");
@@ -620,14 +510,16 @@ print_err("4b\n");
        if (cols>COL11_DATA)
                goto bad_ram;
        /* verify all 4 bytes of dword same */
+/*
        if(cols&0xffff!=(cols>>16)&0xffff)
                goto bad_ram;
        if(cols&0xff!=(cols>>8)&0xff)
                goto bad_ram;
+*/
        print_err("cols"); print_err_hex32(cols); print_err("\n");
        cols -= COL08_DATA;
 
-       /* cols now is in the range of 0 1 2 3 ... 
+       /* cols now is in the range of 0 1 2 3 ...
         */
        i = cols&3;
        //      i = cols + rows;
@@ -641,78 +533,83 @@ print_err("4b\n");
        /* what a fookin' mess this is */
        if(banks==4)
                i+=8; /* <-- i holds merged value */
-       /* i now has the col width in bits 0-1 and the bank count (2 or 4) 
+       /* i now has the col width in bits 0-1 and the bank count (2 or 4)
         * in bit 3.
-        * this is the format for the drccfg register 
+        * this is the format for the drccfg register
         */
-       
+
        /* fix ending addr mask*/
        /*FIXME*/
        /* let's just go with this to start ... see if we can get ANYWHERE */
        /* need to get end addr. Need to do it with the bank in mind. */
-       al = 3; 
+/*
+       al = 3;
        al -= i&3;
-       ending_adr = rows >> al;
-       print_err("computed ending_adr = "); print_err_hex8(ending_adr); 
-       print_err("\r\n");
-       
+       *drcbendaddr = rows >> al;
+       print_err("computed ending_adr = "); print_err_hex8(ending_adr);
+       print_err("\n");
+
+*/
 bad_reinit:
        /* issue all banks recharge */
-       ram->drcctl=0x02;
+       *drcctl=0x02;
        dummy_write();
 
        /* update ending address register */
-       ram->drcbendadr[bank] = ending_adr;
-       
+//     *drcbendadr = ending_adr;
+
        /* update config register */
-       ram->drccfg &= ~(0xff << bank*4);
+       *drccfg &= ~(0xff << bank*4);
        if (ending_adr)
-         ram->drccfg = ((banks = 4 ? 8 : 0) | cols & 3)<< (bank*4);
-       dumpram();
+         *drccfg = ((banks == 4 ? 8 : 0) | cols & 3)<< (bank*4);
+//     dumpram();
        /* skip the rest for now */
        //      bank = 0;
        //      *drccfg=*drccfg&YYY|ZZZZ;
 
        if(bank!=0) {
                bank--;
-               ram->drcbendaddr[bank] = 0xff000000;
+//             drcbendaddr--;
+               *drcbendaddr = 0xff000000;
                //*(&*drcbendadr+XXYYXX)=0xff;
                goto start;
        }
 
        /* set control register to NORMAL mode */
-       ram->drcctl=0x18;
+       *drcctl=0x18;
        dummy_write();
        return bank;
-       
+
 bad_ram:
-       print_info("bad ram!\r\n");
-       /* you are here because the read-after-write failed, 
-        * in most cases because: no ram in that bank! 
+       print_info("bad ram!\n");
+       /* you are here because the read-after-write failed,
+        * in most cases because: no ram in that bank!
         * set badbank to 1 and go to reinit
         */
        ending_adr = 0;
        goto bad_reinit;
-       nextbank(3);
        while(1)
-       print_err("DONE NEXTBANK\r\n");
-
-}      
+       print_err("DONE NEXTBANK\n");
+#endif
+}
 
-/* note: based on AMD code, but AMD code is BROKEN AFAIK */
+/* note: based on AMD code*/
+/* This code is known to work on the digital logic board and on the technologic
+ * systems ts5300
+ */
+int staticmem(void)
+{
+       volatile unsigned long *zero = (unsigned long *) CACHELINESZ;
 
-int
-staticmem(void){
-       volatile unsigned char *zero = (unsigned char *) 0;
        /* set up 0x18 .. **/
        *drcbendadr = 0x88;
-       *drctmctl = 0x1e;
+       *drcmctl = 0x1e;
        *drccfg = 0x9;
        /* nop mode */
        *drcctl = 0x1;
        /* do the dummy write */
        *zero = 0;
-       
+
        /* precharge */
        *drcctl = 2;
        *zero = 0;
@@ -720,17 +617,27 @@ staticmem(void){
        /* two autorefreshes */
        *drcctl = 4;
        *zero = 0;
-       print_err("one zero out on refresh\r\n");
+       print_debug("one zero out on refresh\n");
        *zero = 0;
-       print_err("two zero out on refresh\r\n");
+       print_debug("two zero out on refresh\n");
 
        /* load mode register */
        *drcctl = 3;
        *zero = 0;
-       print_err("DONE the load mode reg\r\n");
-       
+       print_debug("DONE the load mode reg\n");
+
        /* normal mode */
+       *drcctl = 0x0;
+       *zero = 0;
+       print_debug("DONE one last write and then turn on refresh etc\n");
        *drcctl = 0x18;
        *zero = 0;
-       print_err("DONE the normal\r\n");
+       print_debug("DONE the normal\n");
+       *zero = 0xdeadbeef;
+       if (*zero != 0xdeadbeef)
+         print_debug("NO LUCK\n");
+       else
+         print_debug("did a store and load ...\n");
+       //print_err_hex32(*zero);
+       //      print_err(" zero is now "); print_err_hex32(*zero); print_err("\n");
 }