[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[XenPPC] [pushed] [ppc] U4 DART enablement for JS21



changeset:   9958:786d4a84bdad6467f780967e7725581f44678d9a
user:        jimix@xxxxxxxxxxxxxxxxxxxxx
date:        Fri Apr 28 17:44:52 2006 -0400
files:       xen/arch/ppc/Makefile xen/arch/ppc/boot_of.c xen/arch/ppc/dart.c 
xen/arch/ppc/dart.h xen/arch/ppc/dart_u4.c xen/arch/ppc/iommu_u3.c
description:
[ppc] U4 DART enablement for JS21
  - discover the DART and model from the devtree
  - place common code in single file
  - isolate U3 DART code
  - write U4 DART code
  - rewrite invalidate retry code so it actually makes sense


diff -r ffa41af2e455738f8fe3a0af8ae8952e9d4cc47c -r 
786d4a84bdad6467f780967e7725581f44678d9a xen/arch/ppc/Makefile
--- a/xen/arch/ppc/Makefile     Thu Apr 27 14:40:10 2006 -0400
+++ b/xen/arch/ppc/Makefile     Fri Apr 28 17:44:52 2006 -0400
@@ -8,6 +8,8 @@ obj-y += audit.o
 obj-y += audit.o
 obj-y += bitops.o
 obj-y += boot_of.o
+obj-y += dart.o
+obj-y += dart_u4.o
 obj-y += delay.o
 obj-y += dom0_ops.o
 obj-y += domain_build.o
diff -r ffa41af2e455738f8fe3a0af8ae8952e9d4cc47c -r 
786d4a84bdad6467f780967e7725581f44678d9a xen/arch/ppc/boot_of.c
--- a/xen/arch/ppc/boot_of.c    Thu Apr 27 14:40:10 2006 -0400
+++ b/xen/arch/ppc/boot_of.c    Fri Apr 28 17:44:52 2006 -0400
@@ -24,6 +24,7 @@
 #include <xen/compile.h>
 #include <public/of-devtree.h>
 #include <asm/page.h>
+#include "dart.h"
 
 static ulong of_vec;
 static ulong of_msr;
@@ -824,15 +825,12 @@ static void boot_of_module(ulong r3, ulo
     mbi->flags |= MBI_MODULES;
     mbi->mods_count = 2;
     mbi->mods_addr = (u32)mods;
-
 }
 
 
 static int __init boot_of_serial(void)
 {
-    /* right now we are punting and using mambo writes which is the
-     * hardcoded setup */
-
+    /* fill this in */
     return 1;
 }
 
@@ -889,6 +887,35 @@ static void __init boot_of_pic(void)
         opic_addr |= addr[1];
     }
     of_printf("OF: found OpenPIC at: 0x%lx\n", opic_addr);
+}
+
+static void __init boot_of_dart(void)
+{
+    int n;
+
+    n = of_finddevice("/mambo");
+    if (n != OF_FAILURE) {
+        /* mambo had no dart */
+        return;
+    }
+
+    /* defaults */
+    dart_address = DART_DEF_BASE;
+    dart_model = DART_U3;
+
+    /* this is not great but is sufficient */
+    n = of_finddevice("/dart");
+    if (n != OF_FAILURE) {
+        char compat[128];
+
+        of_getprop(n, "reg", &dart_address, sizeof (dart_address));
+
+        compat[0] = '\0';
+        of_getprop(n, "compatible", compat, sizeof (compat));
+        if (strstr(compat, "u4")) {
+            dart_model = DART_U4;
+        }
+    }
 }
 
 multiboot_info_t __init *boot_of_init(
@@ -928,6 +955,7 @@ multiboot_info_t __init *boot_of_init(
     boot_of_cpus();
     boot_of_rtas();
     boot_of_pic();
+    boot_of_dart();
 
     /* end of OF */
     of_printf("closing OF stdout...\n");
diff -r ffa41af2e455738f8fe3a0af8ae8952e9d4cc47c -r 
786d4a84bdad6467f780967e7725581f44678d9a xen/arch/ppc/iommu_u3.c
--- a/xen/arch/ppc/iommu_u3.c   Thu Apr 27 14:40:10 2006 -0400
+++ b/xen/arch/ppc/iommu_u3.c   Fri Apr 28 17:44:52 2006 -0400
@@ -21,18 +21,13 @@
 #include <xen/config.h>
 #include <xen/types.h>
 #include <xen/sched.h>
-#include <xen/init.h>
 #include <xen/mm.h>
 #include <public/xen.h>
 #include <asm/io.h>
 #include <asm/current.h>
 #include "tce.h"
 #include "iommu.h"
-
-#define DART_VALID  0x80000000
-#define DART_MASK   0x00ffffff
-#define DART_BASE   0xf8033000UL
-#define DART_SHIFT  21
+#include "dart.h"
 
 union dart_ctl {
     u32 dc_word;
@@ -45,162 +40,67 @@ union dart_ctl {
     } reg;
 };
 
-#ifdef DEBUG
-static int first_put = 0;
-#endif
+static u32 volatile *dart_ctl_reg;
 
-static u32 *dart_table;
-static ulong dummy_page;
-static u32 *dart_ctl_reg;
+static void u3_inv_all(void)
+{
+    union dart_ctl dc;
+    ulong r = 0;
+    int l = 0;
 
-static void fill_dart(ulong index, ulong rpg, ulong num_pg)
-{
-    u32 volatile *entry = dart_table + index;
-    ulong i = 0;
-    ulong last_flush = 0;
+    for (;;) {
+        dc.dc_word = in_32(dart_ctl_reg);
+        dc.reg.dc_invtlb = 1;
+        out_32(dart_ctl_reg, dc.dc_word);
 
-    while (1) {
-        entry[i] = DART_VALID | (rpg & DART_MASK);
-        ++i;
-        ++rpg;
-        if (i == num_pg) break;
+    do {
+        dc.dc_word = in_32(dart_ctl_reg);
+        r++;
+    } while ((dc.reg.dc_invtlb == 1) && (r < (1 << l)));
 
-        if (((ulong)&entry[i]) % CACHE_LINE_SIZE == 0) {
-            last_flush = (ulong)&entry[i - 1];
-            dcbst(last_flush);
+        if (r == (1 << l)) {
+            if (l < 4) {
+                l++;
+                dc.dc_word = in_32(dart_ctl_reg);
+                dc.reg.dc_invtlb = 0;
+                out_32(dart_ctl_reg, dc.dc_word);
+                continue;
+            } else {
+                panic(" broken U3???\n");
+            }
         }
+        return;
     }
-    dcbst((ulong) &entry[i - 1]);
 }
 
-static void clear_dart(ulong index, ulong num_pg)
+static void u3_inv_entry(ulong pg)
 {
-    u32 *entry = dart_table + index;
-    ulong i = 0;
-    ulong rpg = dummy_page;
-    ulong last_flush = 0;
-
-    while (1) {
-        entry[i] = DART_VALID | (rpg & DART_MASK);
-        ++i;
-        if (i == num_pg) break;
-
-        if (((ulong)&entry[i]) % CACHE_LINE_SIZE == 0) {
-            last_flush = (ulong)&entry[i - 1];
-            dcbst(last_flush);
-        }
-    }
-    dcbst((ulong)&entry[i - 1]);
+    /* sadly single entry invalidation has been reported not to work */
+    u3_inv_all();
 }
 
-static void invtlb_dart(void)
+static struct dart_ops u3_ops = {
+    .do_inv_all = u3_inv_all,
+    .do_inv_entry = u3_inv_entry,
+};
+
+struct dart_ops *u3_init(ulong base, ulong table, ulong tpgs)
 {
     union dart_ctl dc;
-    ulong retries = 0;
 
-    dc.dc_word = in_32(dart_ctl_reg);
-    dc.reg.dc_invtlb = 1;
+    dart_ctl_reg = (u32 *)base;
+
+    dc.dc_word = 0;
+
+    dc.reg.dc_base = table >> PAGE_SHIFT;
+    dc.reg.dc_size = 1 << tpgs;
+    dc.reg.dc_enable = 1;
+
+
+    printk("Initializing DART Model U3: reg: %p word: %x\n",
+           dart_ctl_reg, dc.dc_word);
 
     out_32(dart_ctl_reg, dc.dc_word);
 
-    do {
-        union dart_ctl copy;
-
-        copy.dc_word = in_32(dart_ctl_reg);
-        if (copy.reg.dc_invtlb == 0) {
-            break;
-        }
-
-        ++retries;
-        if ((retries & 3) == 0) {
-            copy.reg.dc_invtlb = 0;
-            out_32(dart_ctl_reg, copy.dc_word);
-            copy.dc_word = in_32(dart_ctl_reg);
-            out_32(dart_ctl_reg, dc.dc_word);
-        }
-    } while (1);
+    return &u3_ops;
 }
-
-static int u3_put(ulong ioba, union tce tce)
-{
-    ulong index = ioba >> PAGE_SHIFT;
-
-    if (index > (1 << DART_SHIFT) / sizeof(u32)) {
-        return -1;
-    }
-
-    if (tce.tce_bits.tce_vlps  != 0 || tce.tce_bits.tce_lpx != 0) {
-        panic("no support for large TCEs\n");
-    }
-
-    if (tce.tce_bits.tce_read || tce.tce_bits.tce_write) {
-#ifdef DEBUG
-        printk("<DART[0x%lx]: ioba: 0x%lx rpn:0x%lx\n",
-               index, ioba, tce.tce_bits.tce_rpn);
-        first_put = 1;
-#endif
-        fill_dart(index, tce.tce_bits.tce_rpn, 1);
-    } else {
-#ifdef DEBUG
-        if (first_put) {
-            printk(">DART[0x%lx]\n", index);
-        }
-#endif
-        clear_dart(index, 1);
-    }
-    invtlb_dart();
-    
-    return 0;
-}
-
-static int init_u3(void)
-{
-    union dart_ctl dc;
-
-    if (on_mambo()) {
-        return 0;
-    }
-
-    /* SLOF doesn't provide DART address */
-    dart_ctl_reg = (u32 *)DART_BASE;
-
-    /* Max size of 512 pages == 2MB == 1<<21 */
-    dart_table = alloc_xenheap_pages(DART_SHIFT - PAGE_SHIFT);
-
-    /* Linux uses a dummy page, filling "empty" DART entries with a
-       reference to this page to capture stray DMA's */
-    dummy_page = (ulong)alloc_xenheap_pages(1) >> PAGE_SHIFT;
-    memset((void *)(dummy_page << PAGE_SHIFT), 0, 1 << PAGE_SHIFT);
-
-#ifdef DARB_EXAMPLE
-    if (0) {
-        ulong dabr = 0x44590b3; //0xf7fe70b3; //0xc003; // DABR 1013 DABRX 1015
-        ulong dabrx = 0xd;
-        asm volatile("mtspr 1013,%0; mtspr 1015,%1"
-                     : : "r" (dabr), "r" (dabrx) : "memory");
-    }
-#endif
-
-    clear_dart(0, (1 << DART_SHIFT) / sizeof(u32));
-
-    dc.dc_word = 0;
-
-    dc.reg.dc_base = ((ulong)dart_table) >> PAGE_SHIFT;
-    dc.reg.dc_size = 1 << (DART_SHIFT - PAGE_SHIFT);
-    dc.reg.dc_enable = 1;
-
-
-    printk("Initializing U3 DART: tbl: %p[0x%lx] ctl reg: %p word: %x "
-           "dummy: 0x%lx\n",
-           dart_table, (1 << DART_SHIFT) / sizeof(u32),
-           dart_ctl_reg, dc.dc_word, dummy_page);
-
-    out_32(dart_ctl_reg, dc.dc_word);
-
-    invtlb_dart();
-
-    iommu_register(0, u3_put);
-
-    return 0;
-}
-__initcall(init_u3);
diff -r ffa41af2e455738f8fe3a0af8ae8952e9d4cc47c -r 
786d4a84bdad6467f780967e7725581f44678d9a xen/arch/ppc/dart.c
--- /dev/null   Thu Jan  1 00:00:00 1970 +0000
+++ b/xen/arch/ppc/dart.c       Fri Apr 28 17:44:52 2006 -0400
@@ -0,0 +1,194 @@
+/*
+ * Copyright (C) 2005 Jimi Xenidis <jimix@xxxxxxxxxxxxxx>, IBM Corporation
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ * 
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ * 
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
+ */
+#include <xen/config.h>
+#include <xen/types.h>
+#include <xen/mm.h>
+#include <asm/cache.h>
+#include <xen/init.h>
+#include "tce.h"
+#include "iommu.h"
+#include "dart.h"
+
+#undef DEBUG
+#ifdef DEBUG
+static int first_put;
+#endif
+
+#define DART_SHIFT  21
+
+int dart_model;
+unsigned long dart_address;
+
+static ulong dummy_page;
+static struct dart_ops *dops;
+static u32 *dart_table;
+
+union dart_tce {
+    u32 dt_word;
+    struct {
+        u32 dt_v:1;             /* valid */
+        u32 dt_r:1;             /* read */
+        u32 dt_w:1;             /* write */
+        u32 _dt_res:5;
+        u32 dt_ppn:24;         /* 24 bit Physical Page Number
+                                 * representing address [28:51] */
+    } dt_bits;
+};
+
+static u32 dart_encode(int perm, ulong rpn)
+{
+    union dart_tce tce;
+
+    tce.dt_word = 0;
+    tce.dt_bits.dt_v = 1;
+    tce.dt_bits.dt_ppn = rpn;
+
+    if (perm & DART_READ) {
+        tce.dt_bits.dt_r = 1;
+    }
+    if (perm & DART_WRITE) {
+        tce.dt_bits.dt_w = 1;
+    }
+
+    return tce.dt_word;
+}
+
+static void dart_fill(ulong index, int perm, ulong rpg, ulong num_pg)
+{
+    u32 volatile *entry = dart_table + index;
+    ulong i = 0;
+    ulong last_flush = 0;
+
+    while (1) {
+        entry[i] = dart_encode(perm, rpg);
+        ++i;
+        ++rpg;
+        if (i == num_pg) break;
+
+        if (((ulong)&entry[i]) % CACHE_LINE_SIZE == 0) {
+            last_flush = (ulong)&entry[i - 1];
+            dcbst(last_flush);
+        }
+    }
+    dcbst((ulong) &entry[i - 1]);
+}
+
+static void dart_clear(ulong index, ulong num_pg)
+{
+    u32 *entry = dart_table + index;
+    ulong i = 0;
+    ulong rpg = dummy_page;
+    ulong last_flush = 0;
+
+    while (1) {
+        entry[i] = dart_encode(DART_READ | DART_WRITE, rpg);
+        ++i;
+        if (i == num_pg) break;
+
+        if (((ulong)&entry[i]) % CACHE_LINE_SIZE == 0) {
+            last_flush = (ulong)&entry[i - 1];
+            dcbst(last_flush);
+        }
+    }
+    dcbst((ulong)&entry[i - 1]);
+}
+
+static int dart_put(ulong ioba, union tce tce)
+{
+    ulong index = ioba >> PAGE_SHIFT;
+    int perm = 0;
+
+    if (index > (1 << DART_SHIFT) / sizeof(u32)) {
+        return -1;
+    }
+
+    if (tce.tce_bits.tce_vlps  != 0 || tce.tce_bits.tce_lpx != 0) {
+        panic("no support for large TCEs\n");
+    }
+
+    if (tce.tce_bits.tce_read) {
+        perm |= DART_READ;
+    }
+    if (tce.tce_bits.tce_write) {
+        perm |= DART_WRITE;
+    }
+    if (perm != 0) {
+#ifdef DEBUG
+        printk("<DART[0x%lx]: ioba: 0x%lx rpn:0x%lx\n",
+               index, ioba, tce.tce_bits.tce_rpn);
+        first_put = 1;
+#endif
+        dart_fill(index, perm, tce.tce_bits.tce_rpn, 1);
+    } else {
+#ifdef DEBUG
+        if (first_put) {
+            printk(">DART[0x%lx]\n", index);
+        }
+#endif
+        dart_clear(index, 1);
+    }
+    dops->do_inv_entry(tce.tce_bits.tce_rpn);
+    
+    return 0;
+}
+
+static int init_dart(void)
+{
+    ulong tpgs;
+
+    switch (dart_model) {
+    case DART_U3: case DART_U4:
+        break;
+    default:
+        panic("unknown DART model: %d\n", dart_model);
+        /* FALLTHRU */
+    case 0:
+        return 0;
+    }
+
+    /* Max size of 512 pages == 2MB == 1<<21 */
+    tpgs = DART_SHIFT - PAGE_SHIFT;
+    dart_table = alloc_xenheap_pages(tpgs);
+
+    /* Linux uses a dummy page, filling "empty" DART entries with a
+       reference to this page to capture stray DMA's */
+    dummy_page = (ulong)alloc_xenheap_pages(1) >> PAGE_SHIFT;
+    memset((void *)(dummy_page << PAGE_SHIFT), 0, 1 << PAGE_SHIFT);
+
+    printk("Initializing DART 0x%lx: tbl: 0x%lx[0x%lx] dummy: 0x%lx\n",
+           dart_address, (ulong)dart_table, (1 << DART_SHIFT) / sizeof(u32),
+           dummy_page);
+           
+    /* register this iommu */
+    iommu_register(0, dart_put);
+
+    switch (dart_model) {
+    case DART_U3:
+        dops = u3_init(dart_address, (ulong)dart_table, tpgs);
+        break;
+    case DART_U4:
+        dops = u4_init(dart_address, (ulong)dart_table, tpgs);
+        break;
+    }
+
+    dart_clear(0, (1 << DART_SHIFT) / sizeof(u32));
+    dops->do_inv_all();
+printk("%s: done!\n", __func__);
+    return 0;
+}
+__initcall(init_dart);
diff -r ffa41af2e455738f8fe3a0af8ae8952e9d4cc47c -r 
786d4a84bdad6467f780967e7725581f44678d9a xen/arch/ppc/dart.h
--- /dev/null   Thu Jan  1 00:00:00 1970 +0000
+++ b/xen/arch/ppc/dart.h       Fri Apr 28 17:44:52 2006 -0400
@@ -0,0 +1,45 @@
+/*
+ * Copyright (C) 2005 Jimi Xenidis <jimix@xxxxxxxxxxxxxx>, IBM Corporation
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
+ *
+ */
+
+#ifndef _DART_H
+#define _DART_H
+
+#include <xen/config.h>
+#include <xen/types.h>
+
+#define DART_DEF_BASE   0xf8033000UL
+#define DART_NONE 0
+#define DART_U3 3
+#define DART_U4 4
+#define DART_WRITE 0x1
+#define DART_READ 0x2
+
+extern int dart_model;
+extern unsigned long dart_address;
+
+struct dart_ops {
+    void (*do_inv_all)(void);
+    void (*do_inv_entry)(ulong pg);
+};
+
+extern struct dart_ops *u3_init(ulong base, ulong table, ulong tpgs);
+extern struct dart_ops *u4_init(ulong base, ulong table, ulong tpgs);
+
+#endif /* _DART_H */
+
diff -r ffa41af2e455738f8fe3a0af8ae8952e9d4cc47c -r 
786d4a84bdad6467f780967e7725581f44678d9a xen/arch/ppc/dart_u4.c
--- /dev/null   Thu Jan  1 00:00:00 1970 +0000
+++ b/xen/arch/ppc/dart_u4.c    Fri Apr 28 17:44:52 2006 -0400
@@ -0,0 +1,175 @@
+/*
+ * Copyright (C) 2005 Jimi Xenidis <jimix@xxxxxxxxxxxxxx>, IBM Corporation
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation; either version 2 of the License, or
+ * (at your option) any later version.
+ * 
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ * 
+ * You should have received a copy of the GNU General Public License
+ * along with this program; if not, write to the Free Software
+ * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
+ */
+
+#undef DEBUG
+
+#include <xen/config.h>
+#include <xen/types.h>
+#include <xen/sched.h>
+#include <xen/init.h>
+#include <xen/mm.h>
+#include <public/xen.h>
+#include <asm/io.h>
+#include <asm/current.h>
+#include "tce.h"
+#include "iommu.h"
+#include "dart.h"
+
+#define TOO_MANY_RETRIES ~0
+
+union dart_ctl {
+    u32 dc_word;
+    struct {
+        u32 dc_darten:1;      /* DART Enable (0:disabled) */
+        u32 dc_ione:1;        /* Invalidate one DART TLB entry (using ILPN) */
+        u32 dc_iall:1;        /* Invalidate all DART TLB entries */
+        u32 dc_idle:1;        /* DART is idle */
+        u32 dc_peen:1;        /* Parity Checking is enabled */
+        u32 dc_ilpn:27;       /* 27-bit Logical Page Address for 
+                               * invalidating one TLB entry */
+    } dc_bits;
+};
+
+union dart_base {
+    u32 db_word;
+    struct {
+        u32 _db_resv:8;
+        u32 db_dartbase:24;     /* Base Address of DART (4K byte Alignment) */
+    } db_bits;
+};
+
+union dart_size {
+    u32 ds_word;
+    struct {
+        u32 _ds_resv:15;
+        u32 ds_dartsize:17;     /* Size of Dart in 4K-Byte Pages */
+    } ds_bits;
+};
+
+union dart_excp {
+    u32 de_word;
+    struct {
+        u32 de_rqsrc:1;    /* Request Source.  [0:PCIE, 1:HT] */
+        u32 de_lpn:27;     /* 27Ðbit Logical Address of Exception [25:51] */
+        u32 de_rqop:1;     /* Request operation.  [0:Read, 1:Write] */
+        u32 de_xcd:3;      /* Exception code */
+    } de_bits;
+};
+
+struct dart {
+    /* 0x00 */
+    union dart_ctl d_dartcntl;
+    u32 _pad0x04_0x10[3];
+    /* 0x10 */
+    union dart_base d_dartbase;
+    u32 _pad0x14_0x20[3];
+    /* 0x20 */
+    union dart_size d_dartsize;
+    u32 _pad0x24_0x30[3];
+    /* 0x30 */
+    union dart_excp d_dartexcp;
+    u32 _pad0x34_0x40[3];
+};
+
+static volatile struct dart *dart;
+
+static void u4_inv_all(void)
+{
+    union dart_ctl dc;
+    ulong r = 0;
+    int l = 0;
+
+    for (;;) {
+        dc.dc_word = in_32(&dart->d_dartcntl.dc_word);
+        dc.dc_bits.dc_iall = 1;
+        out_32(&dart->d_dartcntl.dc_word, dc.dc_word);
+
+        do {
+            dc.dc_word = in_32(&dart->d_dartcntl.dc_word);
+            r++;
+        } while ((dc.dc_bits.dc_iall == 1) && (r < (1 << l)));
+
+        if (r == (1 << l)) {
+            if (l < 4) {
+                l++;
+                dc.dc_word = in_32(&dart->d_dartcntl.dc_word);
+                dc.dc_bits.dc_iall = 0;
+                out_32(&dart->d_dartcntl.dc_word, dc.dc_word);
+                continue;
+            } else {
+                panic(" broken U4???\n");
+            }
+        }
+        return;
+    }
+}
+
+static void u4_inv_entry(ulong pgn)
+{
+    union dart_ctl dc;
+    ulong retries = 0;
+
+    dc.dc_word = in_32(&dart->d_dartcntl.dc_word);
+    dc.dc_bits.dc_ilpn = pgn;
+    dc.dc_bits.dc_ione = 1;
+    out_32(&dart->d_dartcntl.dc_word, dc.dc_word);
+
+    /* wait for completion */
+    /* FIXME: since we do this from the HV do we need to wait?! */
+    do {
+        dc.dc_word = in_32(&dart->d_dartcntl.dc_word);
+        retries++;
+        if (retries > 1000000)
+            panic("WAY! too long\n");
+    } while (dc.dc_bits.dc_ione != 0);
+}
+
+static struct dart_ops u4_ops = {
+    .do_inv_all = u4_inv_all,
+    .do_inv_entry = u4_inv_entry,
+};
+
+struct dart_ops *u4_init(ulong base, ulong table, ulong tpgs)
+{
+    union dart_base db;
+    union dart_size ds;
+    union dart_ctl dc;
+
+    dart = (struct dart *)base;
+
+    db.db_word = 0;
+    db.db_bits.db_dartbase = table >> PAGE_SHIFT;
+
+    ds.ds_word = 0;
+    ds.ds_bits.ds_dartsize = tpgs;
+
+    dc.dc_word = 0;
+    dc.dc_bits.dc_darten = 1;
+
+    /* make sure its disabled */
+    out_32(&dart->d_dartcntl.dc_word, 0);
+
+    printk("Initializing DART Model U4: ctl: 0x%x base: 0x%x size: 0x%x\n",
+           dc.dc_word, db.db_word, ds.ds_word);
+
+    out_32(&dart->d_dartbase.db_word, db.db_word);
+    out_32(&dart->d_dartsize.ds_word, ds.ds_word);
+    out_32(&dart->d_dartcntl.dc_word, dc.dc_word);
+
+    return &u4_ops;
+}



_______________________________________________
Xen-ppc-devel mailing list
Xen-ppc-devel@xxxxxxxxxxxxxxxxxxx
http://lists.xensource.com/xen-ppc-devel


 


Rackspace

Lists.xenproject.org is hosted with RackSpace, monitoring our
servers 24x7x365 and backed by RackSpace's Fanatical Support®.