root/include/asm-alpha/lca.h

/* [previous][next][first][last][top][bottom][index][help] */

INCLUDED FROM


DEFINITIONS

This source file includes following definitions.
  1. virt_to_bus
  2. bus_to_virt
  3. __inb
  4. __outb
  5. __inw
  6. __outw
  7. __inl
  8. __outl
  9. __readb
  10. __readw
  11. __readl
  12. __writeb
  13. __writew
  14. __writel
  15. readl
  16. writel

   1 #ifndef __ALPHA_LCA__H__
   2 #define __ALPHA_LCA__H__
   3 
   4 /*
   5  * Low Cost Alpha (LCA) definitions (these apply to 21066 and 21068,
   6  * for example).
   7  *
   8  * This file is based on:
   9  *
  10  *      DECchip 21066 and DECchip 21068 Alpha AXP Microprocessors
  11  *      Hardware Reference Manual; Digital Equipment Corp.; May 1994;
  12  *      Maynard, MA; Order Number: EC-N2681-71.
  13  */
  14 
  15 /*
  16  * NOTE: The LCA uses a Host Address Extension (HAE) register to access
  17  *       PCI addresses that are beyond the first 27 bits of address
  18  *       space.  Updating the HAE requires an external cycle (and
  19  *       a memory barrier), which tends to be slow.  Instead of updating
  20  *       it on each sparse memory access, we keep the current HAE value
  21  *       cached in variable cache_hae.  Only if the cached HAE differs
  22  *       from the desired HAE value do we actually updated HAE register.
  23  *       The HAE register is preserved by the interrupt handler entry/exit
  24  *       code, so this scheme works even in the presence of interrupts.
  25  *
  26  * Dense memory space doesn't require the HAE, but is restricted to
  27  * aligned 32 and 64 bit accesses.  Special Cycle and Interrupt
  28  * Acknowledge cycles may also require the use of the HAE.  The LCA
  29  * limits I/O address space to the bottom 24 bits of address space,
  30  * but this easily covers the 16 bit ISA I/O address space.
  31  */
  32 
  33 /*
  34  * NOTE 2! The memory operations do not set any memory barriers, as
  35  * it's not needed for cases like a frame buffer that is essentially
  36  * memory-like.  You need to do them by hand if the operations depend
  37  * on ordering.
  38  *
  39  * Similarly, the port I/O operations do a "mb" only after a write
  40  * operation: if an mb is needed before (as in the case of doing
  41  * memory mapped I/O first, and then a port I/O operation to the same
  42  * device), it needs to be done by hand.
  43  *
  44  * After the above has bitten me 100 times, I'll give up and just do
  45  * the mb all the time, but right now I'm hoping this will work out.
  46  * Avoiding mb's may potentially be a noticeable speed improvement,
  47  * but I can't honestly say I've tested it.
  48  *
  49  * Handling interrupts that need to do mb's to synchronize to
  50  * non-interrupts is another fun race area.  Don't do it (because if
  51  * you do, I'll have to do *everything* with interrupts disabled,
  52  * ugh).
  53  */
  54 
  55 #include <asm/system.h>
  56 
  57 #define LCA_DMA_WIN_BASE        (1024*1024*1024)
  58 #define LCA_DMA_WIN_SIZE        (1024*1024*1024)
  59 
  60 /*
  61  * Memory Controller registers:
  62  */
  63 #define LCA_MEM_BCR0            (IDENT_ADDR + 0x120000000UL)
  64 #define LCA_MEM_BCR1            (IDENT_ADDR + 0x120000008UL)
  65 #define LCA_MEM_BCR2            (IDENT_ADDR + 0x120000010UL)
  66 #define LCA_MEM_BCR3            (IDENT_ADDR + 0x120000018UL)
  67 #define LCA_MEM_BMR0            (IDENT_ADDR + 0x120000020UL)
  68 #define LCA_MEM_BMR1            (IDENT_ADDR + 0x120000028UL)
  69 #define LCA_MEM_BMR2            (IDENT_ADDR + 0x120000030UL)
  70 #define LCA_MEM_BMR3            (IDENT_ADDR + 0x120000038UL)
  71 #define LCA_MEM_BTR0            (IDENT_ADDR + 0x120000040UL)
  72 #define LCA_MEM_BTR1            (IDENT_ADDR + 0x120000048UL)
  73 #define LCA_MEM_BTR2            (IDENT_ADDR + 0x120000050UL)
  74 #define LCA_MEM_BTR3            (IDENT_ADDR + 0x120000058UL)
  75 #define LCA_MEM_GTR             (IDENT_ADDR + 0x120000060UL)
  76 #define LCA_MEM_ESR             (IDENT_ADDR + 0x120000068UL)
  77 #define LCA_MEM_EAR             (IDENT_ADDR + 0x120000070UL)
  78 #define LCA_MEM_CAR             (IDENT_ADDR + 0x120000078UL)
  79 #define LCA_MEM_VGR             (IDENT_ADDR + 0x120000080UL)
  80 #define LCA_MEM_PLM             (IDENT_ADDR + 0x120000088UL)
  81 #define LCA_MEM_FOR             (IDENT_ADDR + 0x120000090UL)
  82 
  83 /*
  84  * I/O Controller registers:
  85  */
  86 #define LCA_IOC_HAE             (IDENT_ADDR + 0x180000000UL)
  87 #define LCA_IOC_CONF            (IDENT_ADDR + 0x180000020UL)
  88 #define LCA_IOC_STAT0           (IDENT_ADDR + 0x180000040UL)
  89 #define LCA_IOC_STAT1           (IDENT_ADDR + 0x180000060UL)
  90 #define LCA_IOC_TBIA            (IDENT_ADDR + 0x180000080UL)
  91 #define LCA_IOC_TB_ENA          (IDENT_ADDR + 0x1800000a0UL)
  92 #define LCA_IOC_SFT_RST         (IDENT_ADDR + 0x1800000c0UL)
  93 #define LCA_IOC_PAR_DIS         (IDENT_ADDR + 0x1800000e0UL)
  94 #define LCA_IOC_W_BASE0         (IDENT_ADDR + 0x180000100UL)
  95 #define LCA_IOC_W_BASE1         (IDENT_ADDR + 0x180000120UL)
  96 #define LCA_IOC_W_MASK0         (IDENT_ADDR + 0x180000140UL)
  97 #define LCA_IOC_W_MASK1         (IDENT_ADDR + 0x180000160UL)
  98 #define LCA_IOC_T_BASE0         (IDENT_ADDR + 0x180000180UL)
  99 #define LCA_IOC_T_BASE1         (IDENT_ADDR + 0x1800001a0UL)
 100 #define LCA_IOC_TB_TAG0         (IDENT_ADDR + 0x188000000UL)
 101 #define LCA_IOC_TB_TAG1         (IDENT_ADDR + 0x188000020UL)
 102 #define LCA_IOC_TB_TAG2         (IDENT_ADDR + 0x188000040UL)
 103 #define LCA_IOC_TB_TAG3         (IDENT_ADDR + 0x188000060UL)
 104 #define LCA_IOC_TB_TAG4         (IDENT_ADDR + 0x188000070UL)
 105 #define LCA_IOC_TB_TAG5         (IDENT_ADDR + 0x1880000a0UL)
 106 #define LCA_IOC_TB_TAG6         (IDENT_ADDR + 0x1880000c0UL)
 107 #define LCA_IOC_TB_TAG7         (IDENT_ADDR + 0x1880000e0UL)
 108 
 109 /*
 110  * Memory spaces:
 111  */
 112 #define LCA_IACK_SC             (IDENT_ADDR + 0x1a0000000UL)
 113 #define LCA_CONF                (IDENT_ADDR + 0x1e0000000UL)
 114 #define LCA_IO                  (IDENT_ADDR + 0x1c0000000UL)
 115 #define LCA_SPARSE_MEM          (IDENT_ADDR + 0x200000000UL)
 116 #define LCA_DENSE_MEM           (IDENT_ADDR + 0x300000000UL)
 117 
 118 /*
 119  * Bit definitions for I/O Controller status register 0:
 120  */
 121 #define LCA_IOC_STAT0_CMD               0xf
 122 #define LCA_IOC_STAT0_ERR               (1<<4)
 123 #define LCA_IOC_STAT0_LOST              (1<<5)
 124 #define LCA_IOC_STAT0_THIT              (1<<6)
 125 #define LCA_IOC_STAT0_TREF              (1<<7)
 126 #define LCA_IOC_STAT0_CODE_SHIFT        8
 127 #define LCA_IOC_STAT0_CODE_MASK         0x7
 128 #define LCA_IOC_STAT0_P_NBR_SHIFT       13
 129 #define LCA_IOC_STAT0_P_NBR_MASK        0x7ffff
 130 
 131 #define HAE_ADDRESS     LCA_IOC_HAE
 132 
 133 #ifdef __KERNEL__
 134 
 135 /*
 136  * Translate physical memory address as seen on (PCI) bus into
 137  * a kernel virtual address and vv.
 138  */
 139 extern inline unsigned long virt_to_bus(void * address)
     /* [previous][next][first][last][top][bottom][index][help] */
 140 {
 141         return virt_to_phys(address) + LCA_DMA_WIN_BASE;
 142 }
 143 
 144 extern inline void * bus_to_virt(unsigned long address)
     /* [previous][next][first][last][top][bottom][index][help] */
 145 {
 146         return phys_to_virt(address - LCA_DMA_WIN_BASE);
 147 }
 148 
 149 /*
 150  * I/O functions:
 151  *
 152  * Unlike Jensen, the Noname machines have no concept of local
 153  * I/O---everything goes over the PCI bus.
 154  *
 155  * There is plenty room for optimization here.  In particular,
 156  * the Alpha's insb/insw/extb/extw should be useful in moving
 157  * data to/from the right byte-lanes.
 158  */
 159 
 160 #define vuip    volatile unsigned int *
 161 
 162 extern inline unsigned int __inb(unsigned long addr)
     /* [previous][next][first][last][top][bottom][index][help] */
 163 {
 164         long result = *(vuip) ((addr << 5) + LCA_IO + 0x00);
 165         result >>= (addr & 3) * 8;
 166         return 0xffUL & result;
 167 }
 168 
 169 extern inline void __outb(unsigned char b, unsigned long addr)
     /* [previous][next][first][last][top][bottom][index][help] */
 170 {
 171         unsigned int w;
 172 
 173         asm ("insbl %2,%1,%0" : "r="(w) : "ri"(addr & 0x3), "r"(b));
 174         *(vuip) ((addr << 5) + LCA_IO + 0x00) = w;
 175         mb();
 176 }
 177 
 178 extern inline unsigned int __inw(unsigned long addr)
     /* [previous][next][first][last][top][bottom][index][help] */
 179 {
 180         long result = *(vuip) ((addr << 5) + LCA_IO + 0x08);
 181         result >>= (addr & 3) * 8;
 182         return 0xffffUL & result;
 183 }
 184 
 185 extern inline void __outw(unsigned short b, unsigned long addr)
     /* [previous][next][first][last][top][bottom][index][help] */
 186 {
 187         unsigned int w;
 188 
 189         asm ("inswl %2,%1,%0" : "r="(w) : "ri"(addr & 0x3), "r"(b));
 190         *(vuip) ((addr << 5) + LCA_IO + 0x08) = w;
 191         mb();
 192 }
 193 
 194 extern inline unsigned int __inl(unsigned long addr)
     /* [previous][next][first][last][top][bottom][index][help] */
 195 {
 196         return *(vuip) ((addr << 5) + LCA_IO + 0x18);
 197 }
 198 
 199 extern inline void __outl(unsigned int b, unsigned long addr)
     /* [previous][next][first][last][top][bottom][index][help] */
 200 {
 201         *(vuip) ((addr << 5) + LCA_IO + 0x18) = b;
 202         mb();
 203 }
 204 
 205 
 206 /*
 207  * Memory functions.  64-bit and 32-bit accesses are done through
 208  * dense memory space, everything else through sparse space.
 209  */
 210 extern inline unsigned long __readb(unsigned long addr)
     /* [previous][next][first][last][top][bottom][index][help] */
 211 {
 212         unsigned long result, shift, msb;
 213 
 214         shift = (addr & 0x3) * 8;
 215         if (addr >= (1UL << 24)) {
 216                 msb = addr & 0xf8000000;
 217                 addr -= msb;
 218                 if (msb != hae.cache) {
 219                         set_hae(msb);
 220                 }
 221         }
 222         result = *(vuip) ((addr << 5) + LCA_SPARSE_MEM + 0x00);
 223         result >>= shift;
 224         return 0xffUL & result;
 225 }
 226 
 227 extern inline unsigned long __readw(unsigned long addr)
     /* [previous][next][first][last][top][bottom][index][help] */
 228 {
 229         unsigned long result, shift, msb;
 230 
 231         shift = (addr & 0x3) * 8;
 232         if (addr >= (1UL << 24)) {
 233                 msb = addr & 0xf8000000;
 234                 addr -= msb;
 235                 if (msb != hae.cache) {
 236                         set_hae(msb);
 237                 }
 238         }
 239         result = *(vuip) ((addr << 5) + LCA_SPARSE_MEM + 0x08);
 240         result >>= shift;
 241         return 0xffffUL & result;
 242 }
 243 
 244 extern inline unsigned long __readl(unsigned long addr)
     /* [previous][next][first][last][top][bottom][index][help] */
 245 {
 246         return *(vuip) (addr + LCA_DENSE_MEM);
 247 }
 248 
 249 extern inline void __writeb(unsigned char b, unsigned long addr)
     /* [previous][next][first][last][top][bottom][index][help] */
 250 {
 251         unsigned long msb;
 252         unsigned int w;
 253 
 254         if (addr >= (1UL << 24)) {
 255                 msb = addr & 0xf8000000;
 256                 addr -= msb;
 257                 if (msb != hae.cache) {
 258                         set_hae(msb);
 259                 }
 260         }
 261         asm ("insbl %2,%1,%0" : "r="(w) : "ri"(addr & 0x3), "r"(b));
 262         *(vuip) ((addr << 5) + LCA_SPARSE_MEM + 0x00) = w;
 263 }
 264 
 265 extern inline void __writew(unsigned short b, unsigned long addr)
     /* [previous][next][first][last][top][bottom][index][help] */
 266 {
 267         unsigned long msb;
 268         unsigned int w;
 269 
 270         if (addr >= (1UL << 24)) {
 271                 msb = addr & 0xf8000000;
 272                 addr -= msb;
 273                 if (msb != hae.cache) {
 274                         set_hae(msb);
 275                 }
 276         }
 277         asm ("inswl %2,%1,%0" : "r="(w) : "ri"(addr & 0x3), "r"(b));
 278         *(vuip) ((addr << 5) + LCA_SPARSE_MEM + 0x08) = w;
 279 }
 280 
 281 extern inline void __writel(unsigned int b, unsigned long addr)
     /* [previous][next][first][last][top][bottom][index][help] */
 282 {
 283         *(vuip) (addr + LCA_DENSE_MEM) = b;
 284 }
 285 
 286 /*
 287  * Most of the above have so much overhead that it probably doesn't
 288  * make sense to have them inlined (better icache behavior).
 289  */
 290 extern unsigned int inb(unsigned long addr);
 291 extern unsigned int inw(unsigned long addr);
 292 extern unsigned int inl(unsigned long addr);
 293 
 294 extern void outb(unsigned char b, unsigned long addr);
 295 extern void outw(unsigned short b, unsigned long addr);
 296 extern void outl(unsigned int b, unsigned long addr);
 297 
 298 extern unsigned long readb(unsigned long addr);
 299 extern unsigned long readw(unsigned long addr);
 300 
 301 extern void writeb(unsigned char b, unsigned long addr);
 302 extern void writew(unsigned short b, unsigned long addr);
 303 
 304 #define inb(port) \
 305 (__builtin_constant_p((port))?__inb(port):(inb)(port))
 306 
 307 #define outb(x, port) \
 308 (__builtin_constant_p((port))?__outb((x),(port)):(outb)((x),(port)))
 309 
 310 #define inb_p inb
 311 #define outb_p outb
 312 
 313 extern inline unsigned long readl(unsigned long addr)
     /* [previous][next][first][last][top][bottom][index][help] */
 314 {
 315         return __readl(addr);
 316 }
 317 
 318 extern inline void writel(unsigned int b, unsigned long addr)
     /* [previous][next][first][last][top][bottom][index][help] */
 319 {
 320         __writel(b, addr);
 321 }
 322 
 323 #undef vuip
 324 
 325 extern unsigned long lca_init (unsigned long mem_start, unsigned long mem_end);
 326 
 327 #endif /* __KERNEL__ */
 328 
 329 /*
 330  * Data structure for handling LCA machine checks.  Correctable errors
 331  * result in a short logout frame, uncorrectably ones in a long one.
 332  */
 333 struct el_lca_mcheck_short {
 334         struct el_common        h;              /* common logout header */
 335         unsigned long           reason;         /* reason for machine check */
 336         unsigned long           esr;            /* error-status register */
 337         unsigned long           ear;            /* error-address register */
 338         unsigned long           dc_stat;        /* dcache status register */
 339         unsigned long           ioc_stat0;      /* I/O controller status register 0 */
 340         unsigned long           ioc_stat1;      /* I/O controller status register 1 */
 341 };
 342 
 343 struct el_lca_mcheck_long {
 344         struct el_common        h;              /* common logout header */
 345         unsigned long           pt[32];         /* PAL temps (pt[0] is reason) */
 346         unsigned long           exc_addr;       /* exception address */
 347         unsigned long           pal_base;       /* PALcode base address */
 348         unsigned long           hier;           /* hw interrupt enable */
 349         unsigned long           hirr;           /* hw interrupt request */
 350         unsigned long           mm_csr;         /* MMU control & status */
 351         unsigned long           dc_stat;        /* data cache status */
 352         unsigned long           dc_addr;        /* data cache addr register */
 353         unsigned long           abox_ctl;       /* address box control register */
 354         unsigned long           esr;            /* error status register */
 355         unsigned long           ear;            /* error address register */
 356         unsigned long           car;            /* cache control register */
 357         unsigned long           ioc_stat0;      /* I/O controller status register 0 */
 358         unsigned long           ioc_stat1;      /* I/O controller status register 1 */
 359         unsigned long           va;             /* virtual address register */
 360 };
 361 
 362 union el_lca {
 363         struct el_common *              c;
 364         struct el_lca_mcheck_long *     l;
 365         struct el_lca_mcheck_short *    s;
 366 };
 367 
 368 #define RTC_PORT(x)     (0x70 + (x))
 369 #define RTC_ADDR(x)     (0x80 | (x))
 370 #define RTC_ALWAYS_BCD  0
 371 
 372 #endif /* __ALPHA_LCA__H__ */

/* [previous][next][first][last][top][bottom][index][help] */