1/*******************************************************************************
2  for Alpha Linux
3*******************************************************************************/
4
5/*
6 *   Create a dependency that should be immune from the effect of register
7 *   renaming as is commonly seen in superscalar processors.  This should
8 *   insert a minimum of 100-ns delays between reads/writes at clock rates
9 *   up to 100 MHz---GGL
10 *
11 *   Slowbcopy(char *src, char *dst, int count)
12 *
13 */
14
15#ifdef HAVE_XORG_CONFIG_H
16#include <xorg-config.h>
17#endif
18
19#include <X11/X.h>
20#include "xf86.h"
21#include "xf86Priv.h"
22#include "xf86_OSlib.h"
23#include "compiler.h"
24
25static int really_slow_bcopy;
26
27void
28xf86SetReallySlowBcopy(void)
29{
30    really_slow_bcopy = 1;
31}
32
33#if defined(__i386__) || defined(__amd64__)
34static void
35xf86_really_slow_bcopy(unsigned char *src, unsigned char *dst, int len)
36{
37    while (len--) {
38        *dst++ = *src++;
39        outb(0x80, 0x00);
40    }
41}
42#endif
43
44/* The outb() isn't needed on my machine, but who knows ... -- ost */
45void
46xf86SlowBcopy(unsigned char *src, unsigned char *dst, int len)
47{
48#if defined(__i386__) || defined(__amd64__)
49    if (really_slow_bcopy) {
50        xf86_really_slow_bcopy(src, dst, len);
51        return;
52    }
53#endif
54    while (len--)
55        *dst++ = *src++;
56}
57
58#ifdef __alpha__
59
60#ifdef __linux__
61
62unsigned long _bus_base(void);
63
64#define useSparse() (!_bus_base())
65
66#define SPARSE (7)
67
68#else
69
70#define useSparse() 0
71
72#define SPARSE 0
73
74#endif
75
76void
77xf86SlowBCopyFromBus(unsigned char *src, unsigned char *dst, int count)
78{
79    if (useSparse()) {
80        unsigned long addr;
81        long result;
82
83        addr = (unsigned long) src;
84        while (count) {
85            result = *(volatile int *) addr;
86            result >>= ((addr >> SPARSE) & 3) * 8;
87            *dst++ = (unsigned char) (0xffUL & result);
88            addr += 1 << SPARSE;
89            count--;
90            outb(0x80, 0x00);
91        }
92    }
93    else
94        xf86SlowBcopy(src, dst, count);
95}
96
97void
98xf86SlowBCopyToBus(unsigned char *src, unsigned char *dst, int count)
99{
100    if (useSparse()) {
101        unsigned long addr;
102
103        addr = (unsigned long) dst;
104        while (count) {
105            *(volatile unsigned int *) addr =
106                (unsigned short) (*src) * 0x01010101;
107            src++;
108            addr += 1 << SPARSE;
109            count--;
110            outb(0x80, 0x00);
111        }
112    }
113    else
114        xf86SlowBcopy(src, dst, count);
115}
116#endif
117