1 /*
2 Copyright 2008 Haiku, Inc. All rights reserved.
3 Distributed under the terms of the MIT license.
4
5 Authors:
6 Gerald Zajac 2008
7 */
8
9 #include "accel.h"
10
11 #include <unistd.h>
12
13
14 // Macros for memory mapped I/O.
15 //==============================
16
17 #define INREG8(addr) *((vuint8*)(gInfo.regs + addr))
18 #define INREG16(addr) *((vuint16*)(gInfo.regs + addr))
19 #define INREG32(addr) *((vuint32*)(gInfo.regs + addr))
20
21 #define OUTREG8(addr, val) *((vuint8*)(gInfo.regs + addr)) = val
22 #define OUTREG16(addr, val) *((vuint16*)(gInfo.regs + addr)) = val
23 #define OUTREG32(addr, val) *((vuint32*)(gInfo.regs + addr)) = val
24
25
26 // Functions for PIO.
27 //===================
28
ReadPIO(uint32 addr,uint8 numBytes)29 uint32 ReadPIO(uint32 addr, uint8 numBytes)
30 {
31 S3GetSetPIO gsp;
32 gsp.magic = S3_PRIVATE_DATA_MAGIC;
33 gsp.offset = addr;
34 gsp.size = numBytes;
35 gsp.value = 0;
36
37 status_t result = ioctl(gInfo.deviceFileDesc, S3_GET_PIO, &gsp, sizeof(gsp));
38 if (result != B_OK)
39 TRACE("ReadPIO() failed, result = 0x%x\n", result);
40
41 return gsp.value;
42 }
43
44
WritePIO(uint32 addr,uint8 numBytes,uint32 value)45 void WritePIO(uint32 addr, uint8 numBytes, uint32 value)
46 {
47 S3GetSetPIO gsp;
48 gsp.magic = S3_PRIVATE_DATA_MAGIC;
49 gsp.offset = addr;
50 gsp.size = numBytes;
51 gsp.value = value;
52
53 status_t result = ioctl(gInfo.deviceFileDesc, S3_SET_PIO, &gsp, sizeof(gsp));
54 if (result != B_OK)
55 TRACE("WritePIO() failed, result = 0x%x\n", result);
56 }
57
58
59 // Functions to read 8/16/32 bit registers.
60 //=========================================
61
ReadReg8(uint32 addr)62 uint8 ReadReg8(uint32 addr)
63 {
64 if (gInfo.sharedInfo->chipType == S3_TRIO64)
65 return ReadPIO(addr, 1);
66
67 return INREG8(addr);
68 }
69
70
ReadReg16(uint32 addr)71 uint16 ReadReg16(uint32 addr)
72 {
73 if (gInfo.sharedInfo->chipType == S3_TRIO64)
74 return ReadPIO(addr, 2);
75
76 return INREG16(addr);
77 }
78
79
ReadReg32(uint32 addr)80 uint32 ReadReg32(uint32 addr)
81 {
82 if (gInfo.sharedInfo->chipType == S3_TRIO64)
83 return ReadPIO(addr, 4);
84
85 return INREG32(addr);
86 }
87
88
89 // Functions to write 8/16/32 bit registers.
90 //=========================================
91
WriteReg8(uint32 addr,uint8 value)92 void WriteReg8(uint32 addr, uint8 value)
93 {
94 if (gInfo.sharedInfo->chipType == S3_TRIO64)
95 WritePIO(addr, 1, value);
96 else
97 OUTREG8(addr, value);
98 }
99
100
WriteReg16(uint32 addr,uint16 value)101 void WriteReg16(uint32 addr, uint16 value)
102 {
103 if (gInfo.sharedInfo->chipType == S3_TRIO64)
104 WritePIO(addr, 2, value);
105 else
106 OUTREG16(addr, value);
107 }
108
109
WriteReg32(uint32 addr,uint32 value)110 void WriteReg32(uint32 addr, uint32 value)
111 {
112 if (gInfo.sharedInfo->chipType == S3_TRIO64)
113 WritePIO(addr, 4, value);
114 else
115 OUTREG32(addr, value);
116 }
117
118
119 // Functions to read/write CRTC registers.
120 //========================================
121
ReadCrtcReg(uint8 index)122 uint8 ReadCrtcReg(uint8 index)
123 {
124 if (gInfo.sharedInfo->chipType == S3_TRIO64) {
125 WritePIO_8(0x3d4, index);
126 return ReadPIO_8(0x3d5);
127 }
128
129 OUTREG8(0x83d4, index);
130 return INREG8(0x83d5);
131 }
132
133
WriteCrtcReg(uint8 index,uint8 value)134 void WriteCrtcReg(uint8 index, uint8 value)
135 {
136 if (gInfo.sharedInfo->chipType == S3_TRIO64) {
137 WritePIO_8(0x3d4, index);
138 WritePIO_8(0x3d5, value);
139 } else {
140 OUTREG8(0x83d4, index);
141 OUTREG8(0x83d5, value);
142 }
143 }
144
145
WriteCrtcReg(uint8 index,uint8 value,uint8 mask)146 void WriteCrtcReg(uint8 index, uint8 value, uint8 mask)
147 {
148 // Write a value to a CRTC reg using a mask. The mask selects the
149 // bits to be modified.
150
151 if (gInfo.sharedInfo->chipType == S3_TRIO64) {
152 WritePIO_8(0x3d4, index);
153 WritePIO_8(0x3d5, (ReadPIO_8(0x3d5) & ~mask) | (value & mask));
154 } else {
155 OUTREG8(0x83d4, index);
156 OUTREG8(0x83d5, (INREG8(0x83d5) & ~mask) | (value & mask));
157 }
158 }
159
160
161 // Functions to read/write Sequence registers.
162 //============================================
163
ReadSeqReg(uint8 index)164 uint8 ReadSeqReg(uint8 index)
165 {
166 if (gInfo.sharedInfo->chipType == S3_TRIO64) {
167 WritePIO_8(0x3c4, index);
168 return ReadPIO_8(0x3c5);
169 }
170
171 OUTREG8(0x83c4, index);
172 return INREG8(0x83c5);
173 }
174
175
WriteSeqReg(uint8 index,uint8 value)176 void WriteSeqReg(uint8 index, uint8 value)
177 {
178 if (gInfo.sharedInfo->chipType == S3_TRIO64) {
179 WritePIO_8(0x3c4, index);
180 WritePIO_8(0x3c5, value);
181 } else {
182 OUTREG8(0x83c4, index);
183 OUTREG8(0x83c5, value);
184 }
185 }
186
187
WriteSeqReg(uint8 index,uint8 value,uint8 mask)188 void WriteSeqReg(uint8 index, uint8 value, uint8 mask)
189 {
190 // Write a value to a Sequencer reg using a mask. The mask selects the
191 // bits to be modified.
192
193 if (gInfo.sharedInfo->chipType == S3_TRIO64) {
194 WritePIO_8(0x3c4, index);
195 WritePIO_8(0x3c5, (ReadPIO_8(0x3c5) & ~mask) | (value & mask));
196 } else {
197 OUTREG8(0x83c4, index);
198 OUTREG8(0x83c5, (INREG8(0x83c5) & ~mask) | (value & mask));
199 }
200 }
201
202
203 // Functions to read/write the misc output register.
204 //==================================================
205
ReadMiscOutReg()206 uint8 ReadMiscOutReg()
207 {
208 if (gInfo.sharedInfo->chipType == S3_TRIO64)
209 return ReadPIO_8(0x3cc);
210
211 return INREG8(0x83cc);
212 }
213
214
WriteMiscOutReg(uint8 value)215 void WriteMiscOutReg(uint8 value)
216 {
217 if (gInfo.sharedInfo->chipType == S3_TRIO64)
218 WritePIO_8(0x3c2, value);
219 else
220 OUTREG8(0x83c2, value);
221 }
222
223
WriteIndexedColor(uint8 index,uint8 red,uint8 green,uint8 blue)224 void WriteIndexedColor(uint8 index, uint8 red, uint8 green, uint8 blue)
225 {
226 // Write an indexed color. Argument index is the index (0-255) of the
227 // color, and arguments red, green, & blue are the components of the color.
228
229 // Note that although the Trio64V+ chip supports MMIO in nearly all areas,
230 // it does not support MMIO for setting indexed colors; thus, use PIO to
231 // set the indexed color.
232
233 if (gInfo.sharedInfo->chipType == S3_TRIO64
234 || gInfo.sharedInfo->chipType == S3_TRIO64_VP) {
235 WritePIO_8(0x3c8, index); // color index
236 WritePIO_8(0x3c9, red);
237 WritePIO_8(0x3c9, green);
238 WritePIO_8(0x3c9, blue);
239 } else {
240 OUTREG8(0x83c8, index); // color index
241 OUTREG8(0x83c9, red);
242 OUTREG8(0x83c9, green);
243 OUTREG8(0x83c9, blue);
244 }
245 }
246