BPicture: Fix archive constructor.
[haiku.git] / src / add-ons / kernel / drivers / graphics / radeon_hd / driver.cpp
blob2f2df49c7eed24a4e26864cfa214c378e6888abf
1 /*
2 * Copyright (c) 2002, Thomas Kurschel
3 * Copyright 2004-2011 Haiku, Inc. All rights reserved.
4 * Distributed under the terms of the MIT License.
6 * Authors:
7 * Thomas Kurschel
8 * Clemens Zeidler, <haiku@clemens-zeidler.de>
9 * Alexander von Gluck IV, kallisti5@unixzen.com
13 #include "driver.h"
14 #include "device.h"
15 #include "lock.h"
17 #include <stdlib.h>
18 #include <stdio.h>
19 #include <string.h>
21 #include <AGP.h>
22 #include <KernelExport.h>
23 #include <OS.h>
24 #include <PCI.h>
25 #include <SupportDefs.h>
28 #define TRACE_DRIVER
29 #ifdef TRACE_DRIVER
30 # define TRACE(x...) dprintf("radeon_hd: " x)
31 #else
32 # define TRACE(x...) ;
33 #endif
35 #define ERROR(x...) dprintf("radeon_hd: " x)
37 #define MAX_CARDS 1
40 // ATI / AMD cards starting at the Radeon X700 have an AtomBIOS
42 // list of supported devices
43 const struct supported_device {
44 uint32 pciID;
45 uint8 dceMajor; // Display block family
46 uint8 dceMinor; // Display block family
47 uint16 chipsetID;
48 uint32 chipsetFlags;
49 const char* deviceName;
50 } kSupportedDevices[] = {
51 // Marketing Names: Radeon X?00
52 // Intorduced: 2004
53 // Codename: Loki
54 // R420 Series (Radeon) DCE 0.0 (*very* early AtomBIOS)
56 // Marketing Names: Radeon X1?00
57 // Introduced: 2005
58 // Codename: Fudo
59 #if 0
60 {0x791e, 1, 0, RADEON_RS690, CHIP_IGP, "Radeon X1200"},
61 {0x791f, 1, 0, RADEON_RS690, CHIP_IGP, "Radeon X1200"},
62 {0x793f, 1, 0, RADEON_RS600, CHIP_IGP, "Radeon X1200"},
63 {0x7941, 1, 0, RADEON_RS600, CHIP_IGP, "Radeon X1200"},
64 {0x7942, 1, 0, RADEON_RS600, CHIP_IGP, "Radeon X1250"},
65 {0x796c, 1, 0, RADEON_RS740, CHIP_IGP, "Radeon RS740"},
66 {0x796d, 1, 0, RADEON_RS740, CHIP_IGP, "Radeon RS740"},
67 {0x796e, 1, 0, RADEON_RS740, CHIP_IGP, "Radeon 2100"},
68 {0x796f, 1, 0, RADEON_RS740, CHIP_IGP, "Radeon RS740"},
69 {0x7140, 1, 0, RADEON_RV515, CHIP_STD, "Radeon X1600"},
70 {0x7100, 1, 0, RADEON_R520, CHIP_STD, "Radeon X1800"},
71 {0x7104, 1, 0, RADEON_R520, CHIP_STD, "FireGL v7200"},
72 {0x7109, 1, 0, RADEON_R520, CHIP_STD, "Radeon X1800"},
73 {0x710a, 1, 0, RADEON_R520, CHIP_STD, "Radeon X1800"},
74 {0x710b, 1, 0, RADEON_R520, CHIP_STD, "Radeon X1800"},
75 {0x710c, 1, 0, RADEON_R520, CHIP_STD, "Radeon X1800"},
76 {0x7120, 1, 0, RADEON_R520, CHIP_STD, "Radeon X1800"},
77 {0x7129, 1, 0, RADEON_R520, CHIP_STD, "Radeon X1800"},
78 #endif
80 // Marketing Names: Radeon HD 24xx - HD 42xx
81 // Introduced: 2006
82 // Codename: Pele
83 // Process: 55 nm
84 {0x94c7, 2, 0, RADEON_RV610, CHIP_STD, "Radeon HD 2350"},
85 {0x94c1, 2, 0, RADEON_RV610, CHIP_IGP, "Radeon HD 2400"},
86 {0x94c3, 2, 0, RADEON_RV610, CHIP_STD, "Radeon HD 2400"},
87 {0x94c9, 2, 0, RADEON_RV610, CHIP_IGP, "Mobility Radeon HD 2400"},
88 {0x94cc, 2, 0, RADEON_RV610, CHIP_STD, "Radeon HD 2400"},
89 {0x9519, 2, 0, RADEON_RV630, CHIP_STD, "AMD FireStream 9170"},
90 {0x9586, 2, 0, RADEON_RV630, CHIP_STD, "Radeon HD 2600"},
91 {0x9588, 2, 0, RADEON_RV630, CHIP_STD, "Radeon HD 2600"},
92 {0x958a, 2, 0, RADEON_RV630, CHIP_STD, "Radeon HD 2600 X2"},
93 // Radeon 2700 - RV630
94 {0x9400, 2, 0, RADEON_R600, CHIP_STD, "Radeon HD 2900"},
95 {0x9401, 2, 0, RADEON_R600, CHIP_STD, "Radeon HD 2900"},
96 {0x9402, 2, 0, RADEON_R600, CHIP_STD, "Radeon HD 2900"},
97 {0x9403, 2, 0, RADEON_R600, CHIP_STD, "Radeon HD 2900 Pro"},
98 {0x9405, 2, 0, RADEON_R600, CHIP_STD, "Radeon HD 2900"},
99 {0x940a, 2, 0, RADEON_R600, CHIP_STD, "Radeon FireGL V8650"},
100 {0x940b, 2, 0, RADEON_R600, CHIP_STD, "Radeon FireGL V8600"},
101 {0x940f, 2, 0, RADEON_R600, CHIP_STD, "Radeon FireGL V7600"},
102 {0x9616, 2, 0, RADEON_RV610, CHIP_IGP, "Radeon HD 3000"},
103 {0x9611, 3, 0, RADEON_RV620, CHIP_IGP, "Radeon HD 3100"},
104 {0x9613, 3, 0, RADEON_RV620, CHIP_IGP, "Radeon HD 3100"},
105 {0x9610, 2, 0, RADEON_RV610, CHIP_IGP, "Radeon HD 3200"},
106 {0x9612, 2, 0, RADEON_RV610, CHIP_IGP, "Radeon HD 3200"},
107 {0x9615, 2, 0, RADEON_RV610, CHIP_IGP, "Radeon HD 3200"},
108 {0x9614, 2, 0, RADEON_RV610, CHIP_IGP, "Radeon HD 3300"},
109 // Radeon 3430 - RV620
110 {0x95c2, 3, 0, RADEON_RV620, CHIP_STD, "Radeon HD 3430"},
111 {0x95c5, 3, 0, RADEON_RV620, CHIP_STD, "Radeon HD 3450"},
112 {0x95c6, 3, 0, RADEON_RV620, CHIP_STD, "Radeon HD 3450"},
113 {0x95c7, 3, 0, RADEON_RV620, CHIP_STD, "Radeon HD 3450"},
114 {0x95c9, 3, 0, RADEON_RV620, CHIP_STD, "Radeon HD 3450"},
115 {0x95c4, 3, 0, RADEON_RV620, CHIP_STD, "Radeon HD 3470"},
116 {0x95c0, 3, 0, RADEON_RV620, CHIP_STD, "Radeon HD 3550"},
117 {0x9581, 2, 0, RADEON_RV630, CHIP_STD, "Radeon HD 3600"},
118 {0x9583, 2, 0, RADEON_RV630, CHIP_STD, "Radeon HD 3600"},
119 {0x9598, 2, 0, RADEON_RV630, CHIP_STD, "Radeon HD 3600"},
120 {0x9591, 3, 0, RADEON_RV635, CHIP_STD, "Radeon HD 3600"},
121 {0x9589, 2, 0, RADEON_RV630, CHIP_STD, "Radeon HD 3610"},
122 // Radeon 3650 - RV635
123 // Radeon 3670 - RV635
124 {0x9507, 2, 0, RADEON_RV670, CHIP_STD, "Radeon HD 3830"},
125 {0x9505, 2, 0, RADEON_RV670, CHIP_STD, "Radeon HD 3850"},
126 {0x9513, 2, 0, RADEON_RV670, CHIP_STD, "Radeon HD 3850 X2"},
127 {0x9515, 2, 0, RADEON_RV670, CHIP_STD, "Radeon HD 3850"},
128 {0x9501, 2, 0, RADEON_RV670, CHIP_STD, "Radeon HD 3870"},
129 {0x950F, 2, 0, RADEON_RV670, CHIP_STD | CHIP_X2, "Radeon HD 3870 X2"},
130 {0x9710, 3, 0, RADEON_RV620, CHIP_IGP, "Radeon HD 4200"},
131 {0x9715, 3, 0, RADEON_RV620, CHIP_IGP, "Radeon HD 4250"},
132 {0x9712, 3, 0, RADEON_RV620, CHIP_IGP, "Radeon HD 4270"},
133 {0x9714, 3, 0, RADEON_RV620, CHIP_IGP, "Radeon HD 4290"},
135 // Marketing Names: Radeon HD 4330 - HD 4890, HD 51xx, HD 5xxV
136 // Introduced: 2008
137 // Codename: Wekiva
138 // Process: 55 nm
139 // Radeon 4330 - RV710
140 {0x954f, 3, 2, RADEON_RV710, CHIP_IGP, "Radeon HD 4300"},
141 {0x9552, 3, 2, RADEON_RV710, CHIP_IGP, "Radeon HD 4300"},
142 {0x9553, 3, 2, RADEON_RV710, CHIP_IGP, "Radeon HD 4500"},
143 {0x9555, 3, 2, RADEON_RV710, CHIP_STD, "Radeon HD 4350"},
144 {0x9540, 3, 2, RADEON_RV710, CHIP_STD, "Radeon HD 4550"},
145 {0x9452, 3, 2, RADEON_RV730, CHIP_STD, "AMD FireStream 9250"},
146 {0x9480, 3, 2, RADEON_RV730, CHIP_STD, "Radeon HD 4650"},
147 {0x9488, 3, 2, RADEON_RV730, CHIP_MOBILE, "Radeon HD 4650"},
148 {0x9498, 3, 2, RADEON_RV730, CHIP_STD, "Radeon HD 4650"},
149 {0x94b4, 3, 2, RADEON_RV740, CHIP_STD, "Radeon HD 4700"},
150 {0x9490, 3, 2, RADEON_RV730, CHIP_STD, "Radeon HD 4710"},
151 {0x94b3, 3, 2, RADEON_RV740, CHIP_STD, "Radeon HD 4770"},
152 {0x94b5, 3, 2, RADEON_RV740, CHIP_STD, "Radeon HD 4770"},
153 {0x9450, 3, 1, RADEON_RV770, CHIP_STD, "AMD FireStream 9270"},
154 {0x944a, 3, 1, RADEON_RV770, CHIP_MOBILE, "Radeon HD 4850"},
155 {0x944e, 3, 1, RADEON_RV770, CHIP_STD, "Radeon HD 4810"},
156 {0x944c, 3, 1, RADEON_RV770, CHIP_STD, "Radeon HD 4830"},
157 {0x9442, 3, 1, RADEON_RV770, CHIP_STD, "Radeon HD 4850"},
158 {0x9443, 3, 1, RADEON_RV770, CHIP_STD | CHIP_X2, "Radeon HD 4850 X2"},
159 {0x94a1, 3, 1, RADEON_RV770, CHIP_IGP, "Radeon HD 4860"},
160 {0x9440, 3, 1, RADEON_RV770, CHIP_STD, "Radeon HD 4870"},
161 {0x9441, 3, 1, RADEON_RV770, CHIP_STD | CHIP_X2, "Radeon HD 4870 X2"},
162 {0x9460, 3, 1, RADEON_RV770, CHIP_STD, "Radeon HD 4890"},
164 // From here on AMD no longer used numeric identifiers
165 // Marketing names can collide for different generations of cards
166 // as such we should ignore them at all costs (besides the card name)
168 // Introduced: 2009
169 // Codename: Evergreen
170 // Process: 40 nm
171 // Cedar
172 {0x68e1, 4, 0, RADEON_CEDAR, CHIP_STD, "Radeon HD 5430"},
173 {0x68f9, 4, 0, RADEON_CEDAR, CHIP_STD, "Radeon HD 5450"},
174 {0x68e0, 4, 0, RADEON_CEDAR, CHIP_IGP, "Radeon HD 5470"},
175 {0x68e4, 4, 0, RADEON_CEDAR, CHIP_MOBILE, "Radeon HD 6370"},
176 // Redwood
177 {0x68da, 4, 0, RADEON_REDWOOD, CHIP_STD, "Radeon HD 5500"},
178 {0x68d9, 4, 0, RADEON_REDWOOD, CHIP_STD, "Radeon HD 5570"},
179 {0x675f, 4, 0, RADEON_REDWOOD, CHIP_STD, "Radeon HD 5570"},
180 {0x68b9, 4, 0, RADEON_REDWOOD, CHIP_STD, "Radeon HD 5600"},
181 {0x68c1, 4, 0, RADEON_REDWOOD, CHIP_STD, "Radeon HD 5650"},
182 {0x68d8, 4, 0, RADEON_REDWOOD, CHIP_STD, "Radeon HD 5670"},
183 // Juniper
184 {0x68be, 4, 0, RADEON_JUNIPER, CHIP_STD, "Radeon HD 5700"},
185 {0x68b8, 4, 0, RADEON_JUNIPER, CHIP_STD, "Radeon HD 5770"},
186 // Juniper LE / XT (67X0 is rebranded 57X0 + tweaks)
187 {0x68bf, 4, 0, RADEON_JUNIPER, CHIP_STD, "Radeon HD 6750"},
188 {0x68ba, 4, 0, RADEON_JUNIPER, CHIP_STD, "Radeon HD 6770"},
189 // Cypress
190 {0x689e, 4, 0, RADEON_CYPRESS, CHIP_STD, "Radeon HD 5800"},
191 {0x6899, 4, 0, RADEON_CYPRESS, CHIP_STD, "Radeon HD 5850"},
192 {0x6898, 4, 0, RADEON_CYPRESS, CHIP_STD, "Radeon HD 5870"},
193 // Hemlock
194 {0x689c, 4, 0, RADEON_HEMLOCK, CHIP_STD | CHIP_X2, "Radeon HD 5900 X2"},
195 {0x689d, 4, 0, RADEON_HEMLOCK, CHIP_STD | CHIP_X2, "Radeon HD 5900 X2"},
196 // Fusion APUS
197 // Palm
198 {0x9804, 4, 1, RADEON_PALM, CHIP_APU, "Radeon HD 6250"},
199 {0x9805, 4, 1, RADEON_PALM, CHIP_APU, "Radeon HD 6290"},
200 {0x9807, 4, 1, RADEON_PALM, CHIP_APU, "Radeon HD 6290"},
201 {0x9802, 4, 1, RADEON_PALM, CHIP_APU, "Radeon HD 6310"},
202 {0x9803, 4, 1, RADEON_PALM, CHIP_APU, "Radeon HD 6310"},
203 {0x9806, 4, 1, RADEON_PALM, CHIP_APU, "Radeon HD 6320"},
204 // Sumo (no VGA / LVDS!, only DP)
205 {0x9640, 4, 1, RADEON_SUMO, CHIP_APU, "Radeon HD 6550D"},
206 {0x9641, 4, 1, RADEON_SUMO, CHIP_APU, "Radeon HD Sumo"},
207 {0x9647, 4, 1, RADEON_SUMO, CHIP_APU, "Radeon HD 6520G"},
208 {0x9648, 4, 1, RADEON_SUMO, CHIP_APU, "Radeon HD 6480G"},
209 {0x964a, 4, 1, RADEON_SUMO, CHIP_APU, "Radeon HD 6530D"},
210 {0x964e, 4, 1, RADEON_SUMO, CHIP_APU, "Radeon HD Sumo"},
211 {0x964f, 4, 1, RADEON_SUMO, CHIP_APU, "Radeon HD Sumo"},
212 // Sumo2 (no VGA / LVDS!, only DP)
213 {0x9642, 4, 1, RADEON_SUMO2, CHIP_APU, "Radeon HD 6370D"},
214 {0x9643, 4, 1, RADEON_SUMO2, CHIP_APU, "Radeon HD Sumo2"},
215 {0x9644, 4, 1, RADEON_SUMO2, CHIP_APU, "Radeon HD 6410D"},
216 {0x9645, 4, 1, RADEON_SUMO2, CHIP_APU, "Radeon HD Sumo2"},
218 // Introduced: 2010
219 // Codename: Nothern Islands
220 // Process: 40 nm
221 // Caicos
222 {0x6760, 5, 0, RADEON_CAICOS, CHIP_MOBILE, "Radeon HD 6470"},
223 {0x6761, 5, 0, RADEON_CAICOS, CHIP_MOBILE, "Radeon HD 6430"},
224 {0x6762, 5, 0, RADEON_CAICOS, CHIP_STD, "Radeon HD Caicos"},
225 {0x6763, 5, 0, RADEON_CAICOS, CHIP_DISCREET, "Radeon HD E6460"},
226 {0x6764, 5, 0, RADEON_CAICOS, CHIP_STD, "Radeon HD Caicos"},
227 {0x6765, 5, 0, RADEON_CAICOS, CHIP_STD, "Radeon HD Caicos"},
228 {0x6766, 5, 0, RADEON_CAICOS, CHIP_STD, "Radeon HD Caicos"},
229 {0x6767, 5, 0, RADEON_CAICOS, CHIP_STD, "Radeon HD Caicos"},
230 {0x6768, 5, 0, RADEON_CAICOS, CHIP_STD, "Radeon HD Caicos"},
231 {0x6770, 5, 0, RADEON_CAICOS, CHIP_STD, "Radeon HD 6400"},
232 {0x6778, 5, 0, RADEON_CAICOS, CHIP_STD, "Radeon HD 7470/8470"},
233 {0x6779, 5, 0, RADEON_CAICOS, CHIP_STD, "Radeon HD 6450/7450/8450"},
234 {0x68fa, 5, 0, RADEON_CAICOS, CHIP_STD, "Radeon HD 7350"},
235 {0x677b, 5, 0, RADEON_CAICOS, CHIP_STD, "Radeon HD 7400"},
236 {0x6772, 5, 0, RADEON_CAICOS, CHIP_APU, "Radeon HD 7400A"},
237 {0x6771, 5, 0, RADEON_CAICOS, CHIP_STD, "Radeon HD 8490"},
238 // Turks
239 {0x6740, 5, 0, RADEON_TURKS, CHIP_MOBILE, "Radeon HD 6770M"},
240 {0x6741, 5, 0, RADEON_TURKS, CHIP_MOBILE, "Radeon HD 6650M"},
241 {0x6742, 5, 0, RADEON_TURKS, CHIP_MOBILE, "Radeon HD 6625M"},
242 {0x6743, 5, 0, RADEON_TURKS, CHIP_DISCREET, "Radeon HD E6760"},
243 {0x6744, 5, 0, RADEON_TURKS, CHIP_MOBILE, "Radeon HD Turks"},
244 {0x6745, 5, 0, RADEON_TURKS, CHIP_MOBILE, "Radeon HD Turks"},
245 {0x6746, 5, 0, RADEON_TURKS, CHIP_STD, "Radeon HD Turks"},
246 {0x6747, 5, 0, RADEON_TURKS, CHIP_STD, "Radeon HD Turks"},
247 {0x6748, 5, 0, RADEON_TURKS, CHIP_STD, "Radeon HD Turks"},
248 {0x6749, 5, 0, RADEON_TURKS, CHIP_STD, "FirePro v4900"},
249 {0x6750, 5, 0, RADEON_TURKS, CHIP_STD, "Radeon HD 6500"},
250 {0x6758, 5, 0, RADEON_TURKS, CHIP_STD, "Radeon HD 6670"},
251 {0x6759, 5, 0, RADEON_TURKS, CHIP_STD, "Radeon HD 6570/7570"},
252 {0x6850, 6, 0, RADEON_TURKS, CHIP_MOBILE, "Radeon HD 7570"},
253 {0x6840, 6, 0, RADEON_TURKS, CHIP_MOBILE, "Radeon HD 7670"},
254 // Barts
255 {0x673e, 5, 0, RADEON_BARTS, CHIP_STD, "Radeon HD 6790"},
256 {0x6739, 5, 0, RADEON_BARTS, CHIP_STD, "Radeon HD 6850"},
257 {0x6738, 5, 0, RADEON_BARTS, CHIP_STD, "Radeon HD 6870"},
258 // Cayman
259 {0x6700, 5, 0, RADEON_CAYMAN, CHIP_STD, "Radeon HD Cayman"},
260 {0x6701, 5, 0, RADEON_CAYMAN, CHIP_STD, "Radeon HD Cayman"},
261 {0x6702, 5, 0, RADEON_CAYMAN, CHIP_STD, "Radeon HD Cayman"},
262 {0x6703, 5, 0, RADEON_CAYMAN, CHIP_STD, "Radeon HD Cayman"},
263 {0x6704, 5, 0, RADEON_CAYMAN, CHIP_STD, "FirePro v????"},
264 {0x6705, 5, 0, RADEON_CAYMAN, CHIP_STD, "Radeon HD Cayman"},
265 {0x6706, 5, 0, RADEON_CAYMAN, CHIP_STD, "FirePro v????"},
266 {0x6707, 5, 0, RADEON_CAYMAN, CHIP_STD, "Radeon HD Cayman"},
267 {0x6708, 5, 0, RADEON_CAYMAN, CHIP_STD, "Radeon HD Cayman"},
268 {0x6709, 5, 0, RADEON_CAYMAN, CHIP_STD, "Radeon HD Cayman"},
269 {0x6718, 5, 0, RADEON_CAYMAN, CHIP_STD, "Radeon HD 6970"},
270 {0x6719, 5, 0, RADEON_CAYMAN, CHIP_STD, "Radeon HD 6950"},
271 {0x671c, 5, 0, RADEON_CAYMAN, CHIP_STD, "Radeon HD Cayman"},
272 {0x671f, 5, 0, RADEON_CAYMAN, CHIP_STD, "Radeon HD 6900"},
273 // Antilles (Top, Dual GPU)
274 {0x671d, 5, 0, RADEON_ANTILLES, CHIP_STD, "Radeon HD 6990"},
277 // Introduced: Late 2011
278 // Codename: Southern Islands
279 // Process: 28 nm
280 // Cape Verde
281 {0x6820, 6, 0, RADEON_CAPEVERDE, CHIP_STD, "Radeon HD Verde"},
282 {0x6821, 6, 0, RADEON_CAPEVERDE, CHIP_STD, "Radeon HD Verde"},
283 {0x6823, 6, 0, RADEON_CAPEVERDE, CHIP_STD, "Radeon HD Verde"},
284 {0x6824, 6, 0, RADEON_CAPEVERDE, CHIP_STD, "Radeon HD Verde"},
285 {0x6825, 6, 0, RADEON_CAPEVERDE, CHIP_STD, "Radeon HD Verde"},
286 {0x6826, 6, 0, RADEON_CAPEVERDE, CHIP_STD, "Radeon HD Verde"},
287 {0x6827, 6, 0, RADEON_CAPEVERDE, CHIP_STD, "Radeon HD Verde"},
288 {0x6828, 6, 0, RADEON_CAPEVERDE, CHIP_STD, "Radeon HD Verde"},
289 {0x6829, 6, 0, RADEON_CAPEVERDE, CHIP_STD, "Radeon HD Verde"},
290 {0x682a, 6, 0, RADEON_CAPEVERDE, CHIP_STD, "Radeon HD Verde"},
291 {0x682b, 6, 0, RADEON_CAPEVERDE, CHIP_STD, "Radeon HD Verde"},
292 {0x682d, 6, 0, RADEON_CAPEVERDE, CHIP_STD, "Radeon HD Verde"},
293 {0x682f, 6, 0, RADEON_CAPEVERDE, CHIP_STD, "Radeon HD Verde"},
294 {0x6830, 6, 0, RADEON_CAPEVERDE, CHIP_STD, "Radeon HD Verde"},
295 {0x6831, 6, 0, RADEON_CAPEVERDE, CHIP_STD, "Radeon HD Verde"},
296 {0x6835, 6, 0, RADEON_CAPEVERDE, CHIP_STD, "Radeon HD Verde"},
297 {0x6837, 6, 0, RADEON_CAPEVERDE, CHIP_STD, "Radeon HD Verde"},
298 {0x6838, 6, 0, RADEON_CAPEVERDE, CHIP_STD, "Radeon HD Verde"},
299 {0x6839, 6, 0, RADEON_CAPEVERDE, CHIP_STD, "Radeon HD Verde"},
300 {0x683b, 6, 0, RADEON_CAPEVERDE, CHIP_STD, "Radeon HD Verde"},
301 {0x683d, 6, 0, RADEON_CAPEVERDE, CHIP_STD, "Radeon HD 7770"},
302 {0x683f, 6, 0, RADEON_CAPEVERDE, CHIP_STD, "Radeon HD 7750"},
303 // Pitcairn
304 {0x6800, 6, 0, RADEON_PITCAIRN, CHIP_MOBILE, "Radeon HD 7970"},
305 {0x6801, 6, 0, RADEON_PITCAIRN, CHIP_STD, "Radeon HD Pitcairn"},
306 {0x6802, 6, 0, RADEON_PITCAIRN, CHIP_STD, "Radeon HD Pitcairn"},
307 {0x6806, 6, 0, RADEON_PITCAIRN, CHIP_STD, "Radeon HD Pitcairn"},
308 {0x6808, 6, 0, RADEON_PITCAIRN, CHIP_STD, "Radeon HD Pitcairn"},
309 {0x6809, 6, 0, RADEON_PITCAIRN, CHIP_STD, "Radeon HD Pitcairn"},
310 {0x6810, 6, 0, RADEON_PITCAIRN, CHIP_STD, "Radeon HD R9 270X"},
311 {0x6811, 6, 0, RADEON_PITCAIRN, CHIP_STD, "Radeon HD R9 270"},
312 {0x6816, 6, 0, RADEON_PITCAIRN, CHIP_STD, "Radeon HD Pitcairn"},
313 {0x6817, 6, 0, RADEON_PITCAIRN, CHIP_STD, "Radeon HD Pitcairn"},
314 {0x6818, 6, 0, RADEON_PITCAIRN, CHIP_STD, "Radeon HD 7870"},
315 {0x6819, 6, 0, RADEON_PITCAIRN, CHIP_STD, "Radeon HD 7800"},
316 {0x684c, 6, 0, RADEON_PITCAIRN, CHIP_STD, "Radeon HD Pitcairn"},
317 // Tahiti
318 {0x6780, 6, 0, RADEON_TAHITI, CHIP_STD, "Radeon HD Tahiti"},
319 {0x6784, 6, 0, RADEON_TAHITI, CHIP_STD, "Radeon HD Tahiti"},
320 {0x6788, 6, 0, RADEON_TAHITI, CHIP_STD, "Radeon HD Tahiti"},
321 {0x678a, 6, 0, RADEON_TAHITI, CHIP_STD, "Radeon HD Tahiti"},
322 {0x6790, 6, 0, RADEON_TAHITI, CHIP_STD, "Radeon HD Tahiti"},
323 {0x679e, 6, 0, RADEON_TAHITI, CHIP_STD, "Radeon HD Tahiti"},
324 {0x679f, 6, 0, RADEON_TAHITI, CHIP_STD, "Radeon HD Tahiti"},
325 {0x679a, 6, 0, RADEON_TAHITI, CHIP_STD, "Radeon HD 7950"},
326 {0x6798, 6, 0, RADEON_TAHITI, CHIP_STD, "Radeon HD 7970"},
327 {0x6799, 6, 0, RADEON_TAHITI, CHIP_STD, "Radeon HD 7990"},
328 // Aruba DCE 6.1 Trinity / Richland
329 {0x9900, 6, 1, RADEON_ARUBA, CHIP_APU, "Radeon HD 7660"},
330 {0x9901, 6, 1, RADEON_ARUBA, CHIP_APU, "Radeon HD 7660"},
331 {0x9903, 6, 1, RADEON_ARUBA, CHIP_APU, "Radeon HD 7640"},
332 {0x9904, 6, 1, RADEON_ARUBA, CHIP_APU, "Radeon HD 7560"},
333 {0x9905, 6, 1, RADEON_ARUBA, CHIP_APU, "FirePro A300"},
334 {0x9906, 6, 1, RADEON_ARUBA, CHIP_APU, "FirePro A300"},
335 {0x9907, 6, 1, RADEON_ARUBA, CHIP_APU, "Radeon HD 7560"},
336 {0x9908, 6, 1, RADEON_ARUBA, CHIP_APU, "Radeon HD 7620"},
337 {0x9909, 6, 1, RADEON_ARUBA, CHIP_APU, "Radeon HD 7500"},
338 {0x990a, 6, 1, RADEON_ARUBA, CHIP_APU, "Radeon HD 7500"},
339 {0x990b, 6, 1, RADEON_ARUBA, CHIP_APU, "Radeon HD 8650"},
340 {0x990d, 6, 1, RADEON_ARUBA, CHIP_APU, "Radeon HD 8550"},
341 {0x990f, 6, 1, RADEON_ARUBA, CHIP_APU, "Radeon HD 8610"},
342 {0x9910, 6, 1, RADEON_ARUBA, CHIP_APU, "Radeon HD 7660"},
343 {0x9913, 6, 1, RADEON_ARUBA, CHIP_APU, "Radeon HD 7640"},
344 {0x9917, 6, 1, RADEON_ARUBA, CHIP_APU, "Radeon HD 7620"},
345 {0x9918, 6, 1, RADEON_ARUBA, CHIP_APU, "Radeon HD 7600"},
346 {0x9919, 6, 1, RADEON_ARUBA, CHIP_APU, "Radeon HD 7500"},
347 {0x9990, 6, 1, RADEON_ARUBA, CHIP_APU, "Radeon HD 7920"},
348 {0x9991, 6, 1, RADEON_ARUBA, CHIP_APU, "Radeon HD 7540"},
349 {0x9992, 6, 1, RADEON_ARUBA, CHIP_APU, "Radeon HD 7420"},
350 #if 0
351 // Known not to work: https://dev.haiku-os.org/ticket/10606
352 {0x9993, 6, 1, RADEON_ARUBA, CHIP_APU, "Radeon HD 7480"},
353 #endif
354 {0x9994, 6, 1, RADEON_ARUBA, CHIP_APU, "Radeon HD 7400"},
355 {0x9995, 6, 1, RADEON_ARUBA, CHIP_APU, "Radeon HD 8450"},
356 {0x9996, 6, 1, RADEON_ARUBA, CHIP_APU, "Radeon HD 8470"},
357 {0x9997, 6, 1, RADEON_ARUBA, CHIP_APU, "Radeon HD 8350"},
358 {0x9998, 6, 1, RADEON_ARUBA, CHIP_APU, "Radeon HD 8730"},
359 {0x999a, 6, 1, RADEON_ARUBA, CHIP_APU, "Radeon HD 8410"},
360 {0x999b, 6, 1, RADEON_ARUBA, CHIP_APU, "Radeon HD 8310"},
361 {0x999c, 6, 1, RADEON_ARUBA, CHIP_APU, "Radeon HD 8650"},
362 {0x999d, 6, 1, RADEON_ARUBA, CHIP_APU, "Radeon HD 8550"},
363 {0x99a0, 6, 1, RADEON_ARUBA, CHIP_APU, "Radeon HD 7520"},
364 {0x99a2, 6, 1, RADEON_ARUBA, CHIP_APU, "Radeon HD 7420"},
365 {0x99a4, 6, 1, RADEON_ARUBA, CHIP_APU, "Radeon HD 7400"},
366 // Oland DCE 6,4
367 {0x990c, 6, 4, RADEON_OLAND, CHIP_STD, "Radeon HD 8670"},
368 {0x990e, 6, 4, RADEON_OLAND, CHIP_STD, "Radeon HD 8570"},
369 {0x6600, 6, 4, RADEON_OLAND, CHIP_STD, "Radeon HD Oland"},
370 {0x6601, 6, 4, RADEON_OLAND, CHIP_STD, "Radeon HD Oland"},
371 {0x6602, 6, 4, RADEON_OLAND, CHIP_STD, "Radeon HD Oland"},
372 {0x6603, 6, 4, RADEON_OLAND, CHIP_STD, "Radeon HD Oland"},
373 {0x6606, 6, 4, RADEON_OLAND, CHIP_STD, "Radeon HD Oland"},
374 {0x6607, 6, 4, RADEON_OLAND, CHIP_STD, "Radeon HD Oland"},
375 {0x6610, 6, 4, RADEON_OLAND, CHIP_STD, "Radeon HD R7 250"},
376 {0x6611, 6, 4, RADEON_OLAND, CHIP_STD, "Radeon HD Oland"},
377 {0x6613, 6, 4, RADEON_OLAND, CHIP_STD, "Radeon HD R7 240"},
378 {0x6620, 6, 4, RADEON_OLAND, CHIP_STD, "Radeon HD R7 240"},
379 {0x6621, 6, 4, RADEON_OLAND, CHIP_STD, "Radeon HD Oland"},
380 {0x6623, 6, 4, RADEON_OLAND, CHIP_STD, "Radeon HD Oland"},
381 {0x6631, 6, 4, RADEON_OLAND, CHIP_STD, "Radeon HD Oland"},
382 // Hainan NODCE. No display hardware, OpenCL 3D engine.
384 // Introduced: Late 2013
385 // Codename: Sea Islands
386 // Process: 28 nm
387 // Kaveri DCE 8.1
388 {0x1304, 8, 1, RADEON_KAVERI, CHIP_STD, "Radeon HD Kaveri"},
389 {0x1305, 8, 1, RADEON_KAVERI, CHIP_STD, "Radeon HD Kaveri"},
390 {0x1306, 8, 1, RADEON_KAVERI, CHIP_STD, "Radeon HD Kaveri"},
391 {0x1307, 8, 1, RADEON_KAVERI, CHIP_STD, "Radeon HD Kaveri"},
392 {0x1308, 8, 1, RADEON_KAVERI, CHIP_STD, "Radeon HD Kaveri"},
393 {0x1309, 8, 1, RADEON_KAVERI, CHIP_STD, "Radeon HD Kaveri"},
394 {0x130a, 8, 1, RADEON_KAVERI, CHIP_STD, "Radeon HD Kaveri"},
395 {0x130b, 8, 1, RADEON_KAVERI, CHIP_STD, "Radeon HD Kaveri"},
396 {0x130c, 8, 1, RADEON_KAVERI, CHIP_STD, "Radeon HD Kaveri"},
397 {0x130d, 8, 1, RADEON_KAVERI, CHIP_STD, "Radeon HD Kaveri"},
398 {0x130e, 8, 1, RADEON_KAVERI, CHIP_STD, "Radeon HD Kaveri"},
399 {0x130f, 8, 1, RADEON_KAVERI, CHIP_STD, "Radeon HD Kaveri"},
400 {0x1310, 8, 1, RADEON_KAVERI, CHIP_STD, "Radeon HD Kaveri"},
401 {0x1311, 8, 1, RADEON_KAVERI, CHIP_STD, "Radeon HD Kaveri"},
402 {0x1312, 8, 1, RADEON_KAVERI, CHIP_STD, "Radeon HD Kaveri"},
403 {0x1313, 8, 1, RADEON_KAVERI, CHIP_STD, "Radeon HD Kaveri"},
404 {0x1314, 8, 1, RADEON_KAVERI, CHIP_STD, "Radeon HD Kaveri"},
405 {0x1315, 8, 1, RADEON_KAVERI, CHIP_STD, "Radeon HD Kaveri"},
406 {0x1316, 8, 1, RADEON_KAVERI, CHIP_STD, "Radeon HD Kaveri"},
407 {0x1317, 8, 1, RADEON_KAVERI, CHIP_STD, "Radeon HD Kaveri"},
408 {0x131b, 8, 1, RADEON_KAVERI, CHIP_STD, "Radeon HD Kaveri"},
409 {0x131c, 8, 1, RADEON_KAVERI, CHIP_STD, "Radeon HD Kaveri"},
410 {0x131d, 8, 1, RADEON_KAVERI, CHIP_STD, "Radeon HD Kaveri"},
411 // Bonaire DCE 8.2
412 {0x6640, 8, 2, RADEON_BONAIRE, CHIP_MOBILE, "Radeon HD Bonaire"},
413 {0x6641, 8, 2, RADEON_BONAIRE, CHIP_MOBILE, "Radeon HD Bonaire"},
414 {0x6646, 8, 2, RADEON_BONAIRE, CHIP_MOBILE, "Radeon HD Bonaire"},
415 {0x6647, 8, 2, RADEON_BONAIRE, CHIP_MOBILE, "Radeon HD Bonaire"},
416 {0x6649, 8, 2, RADEON_BONAIRE, CHIP_STD, "Radeon HD Bonaire"},
417 {0x6650, 8, 2, RADEON_BONAIRE, CHIP_STD, "Radeon HD Bonaire"},
418 {0x6651, 8, 2, RADEON_BONAIRE, CHIP_STD, "Radeon HD Bonaire"},
419 {0x6658, 8, 2, RADEON_BONAIRE, CHIP_STD, "Radeon HD Bonaire"},
420 {0x665c, 8, 2, RADEON_BONAIRE, CHIP_STD, "Radeon HD 7790"},
421 {0x665d, 8, 2, RADEON_BONAIRE, CHIP_STD, "Radeon HD Bonaire"},
422 {0x665f, 8, 2, RADEON_BONAIRE, CHIP_STD, "Radeon HD Bonaire"},
423 // Kabini DCE 8.3
424 {0x9830, 8, 3, RADEON_KABINI, CHIP_STD, "Radeon HD 8400"},
425 {0x9831, 8, 3, RADEON_KABINI, CHIP_STD, "Radeon HD 8400"},
426 {0x9832, 8, 3, RADEON_KABINI, CHIP_STD, "Radeon HD 8330"},
427 {0x9833, 8, 3, RADEON_KABINI, CHIP_STD, "Radeon HD 8330"},
428 {0x9834, 8, 3, RADEON_KABINI, CHIP_STD, "Radeon HD 8210"},
429 {0x9835, 8, 3, RADEON_KABINI, CHIP_STD, "Radeon HD 8210"},
430 {0x9836, 8, 3, RADEON_KABINI, CHIP_STD, "Radeon HD 8280"},
431 {0x9837, 8, 3, RADEON_KABINI, CHIP_STD, "Radeon HD 8280"},
432 {0x9838, 8, 3, RADEON_KABINI, CHIP_STD, "Radeon HD 8240"},
433 {0x9839, 8, 3, RADEON_KABINI, CHIP_STD, "Radeon HD 8180"},
434 {0x983a, 8, 3, RADEON_KABINI, CHIP_STD, "Radeon HD Kabini"},
435 {0x983b, 8, 3, RADEON_KABINI, CHIP_STD, "Radeon HD Kabini"},
436 {0x983c, 8, 3, RADEON_KABINI, CHIP_STD, "Radeon HD Kabini"},
437 {0x983d, 8, 3, RADEON_KABINI, CHIP_STD, "Radeon HD 8250"},
438 {0x983e, 8, 3, RADEON_KABINI, CHIP_STD, "Radeon HD Kabini"},
439 {0x983f, 8, 3, RADEON_KABINI, CHIP_STD, "Radeon HD Kabini"},
440 // Mullins DCE 8.3
441 {0x9850, 8, 3, RADEON_MULLINS, CHIP_STD, "Radeon HD R3"},
442 {0x9851, 8, 3, RADEON_MULLINS, CHIP_STD, "Radeon HD R2"},
443 {0x9852, 8, 3, RADEON_MULLINS, CHIP_STD, "Radeon HD R2"},
444 {0x9853, 8, 3, RADEON_MULLINS, CHIP_STD, "Radeon HD R2"},
445 {0x9854, 8, 3, RADEON_MULLINS, CHIP_STD, "Radeon HD R2"},
446 {0x9855, 8, 3, RADEON_MULLINS, CHIP_STD, "Radeon HD R3"},
447 {0x9856, 8, 3, RADEON_MULLINS, CHIP_STD, "Radeon HD R2"},
448 {0x9857, 8, 3, RADEON_MULLINS, CHIP_STD, "Radeon HD R2"},
449 {0x9858, 8, 3, RADEON_MULLINS, CHIP_STD, "Radeon HD Mullins"},
450 {0x9859, 8, 3, RADEON_MULLINS, CHIP_STD, "Radeon HD Mullins"},
451 {0x985a, 8, 3, RADEON_MULLINS, CHIP_STD, "Radeon HD Mullins"},
452 {0x985b, 8, 3, RADEON_MULLINS, CHIP_STD, "Radeon HD Mullins"},
453 {0x985c, 8, 3, RADEON_MULLINS, CHIP_STD, "Radeon HD Mullins"},
454 {0x985d, 8, 3, RADEON_MULLINS, CHIP_STD, "Radeon HD Mullins"},
455 {0x985e, 8, 3, RADEON_MULLINS, CHIP_STD, "Radeon HD Mullins"},
456 {0x985f, 8, 3, RADEON_MULLINS, CHIP_STD, "Radeon HD Mullins"},
457 // Hawaii DCE 8.5
458 {0x67a0, 8, 5, RADEON_HAWAII, CHIP_STD, "Radeon HD Hawaii"},
459 {0x67a1, 8, 5, RADEON_HAWAII, CHIP_STD, "Radeon HD Hawaii"},
460 {0x67a2, 8, 5, RADEON_HAWAII, CHIP_STD, "Radeon HD Hawaii"},
461 {0x67a8, 8, 5, RADEON_HAWAII, CHIP_STD, "Radeon HD Hawaii"},
462 {0x67a9, 8, 5, RADEON_HAWAII, CHIP_STD, "Radeon HD Hawaii"},
463 {0x67aa, 8, 5, RADEON_HAWAII, CHIP_STD, "Radeon HD Hawaii"},
464 {0x67b0, 8, 5, RADEON_HAWAII, CHIP_STD, "Radeon HD Hawaii"},
465 {0x67b1, 8, 5, RADEON_HAWAII, CHIP_STD, "Radeon HD Hawaii"},
466 {0x67b8, 8, 5, RADEON_HAWAII, CHIP_STD, "Radeon HD Hawaii"},
467 {0x67b9, 8, 5, RADEON_HAWAII, CHIP_STD, "Radeon HD Hawaii"},
468 {0x67ba, 8, 5, RADEON_HAWAII, CHIP_STD, "Radeon HD Hawaii"},
469 {0x67be, 8, 5, RADEON_HAWAII, CHIP_STD, "Radeon HD Hawaii"},
471 // Introduced: 2014
472 // Codename: Volcanic Islands
473 // Process: 28 nm
474 // Iceland (aka topaz) NO DCE
475 //{0x6900, 99, 0, RADEON_TOPAZ, CHIP_STD, "Radeon HD Topaz"},
476 //{0x6901, 99, 0, RADEON_TOPAZ, CHIP_STD, "Radeon HD Topaz"},
477 //{0x6902, 99, 0, RADEON_TOPAZ, CHIP_STD, "Radeon HD Topaz"},
478 //{0x6903, 99, 0, RADEON_TOPAZ, CHIP_STD, "Radeon HD Topaz"},
479 //{0x6907, 99, 0, RADEON_TOPAZ, CHIP_STD, "Radeon HD Topaz"},
480 // Tonga DCE 10.0
481 {0x6920, 10, 0, RADEON_TONGA, CHIP_STD, "Radeon HD Tonga"},
482 {0x6921, 10, 0, RADEON_TONGA, CHIP_STD, "Radeon HD Tonga"},
483 {0x6928, 10, 0, RADEON_TONGA, CHIP_STD, "Radeon HD Tonga"},
484 {0x6929, 10, 0, RADEON_TONGA, CHIP_STD, "Radeon HD Tonga"},
485 {0x692b, 10, 0, RADEON_TONGA, CHIP_STD, "Radeon HD Tonga"},
486 {0x692f, 10, 0, RADEON_TONGA, CHIP_STD, "Radeon HD Tonga"},
487 {0x6930, 10, 0, RADEON_TONGA, CHIP_STD, "Radeon HD Tonga"},
488 {0x6938, 10, 0, RADEON_TONGA, CHIP_STD, "Radeon HD Tonga"},
489 {0x6939, 10, 0, RADEON_TONGA, CHIP_STD, "Radeon HD Tonga"},
490 // Carrizo DCE 11.0
491 {0x9870, 11, 0, RADEON_CARRIZO, CHIP_APU, "Radeon HD Carrizo"},
492 {0x9874, 11, 0, RADEON_CARRIZO, CHIP_APU, "Radeon HD Carrizo"},
493 {0x9875, 11, 0, RADEON_CARRIZO, CHIP_APU, "Radeon HD Carrizo"},
494 {0x9876, 11, 0, RADEON_CARRIZO, CHIP_APU, "Radeon HD Carrizo"},
495 {0x9877, 11, 0, RADEON_CARRIZO, CHIP_APU, "Radeon HD Carrizo"}
499 int32 api_version = B_CUR_DRIVER_API_VERSION;
502 char* gDeviceNames[MAX_CARDS + 1];
503 radeon_info* gDeviceInfo[MAX_CARDS];
504 pci_module_info* gPCI;
505 mutex gLock;
508 static status_t
509 get_next_radeon_hd(int32* _cookie, pci_info &info, uint32 &type)
511 int32 index = *_cookie;
513 // find devices
515 for (; gPCI->get_nth_pci_info(index, &info) == B_OK; index++) {
516 // check vendor
517 if (info.vendor_id != VENDOR_ID_ATI
518 || info.class_base != PCI_display
519 || info.class_sub != PCI_vga)
520 continue;
522 // check device
523 for (uint32 i = 0; i < sizeof(kSupportedDevices)
524 / sizeof(kSupportedDevices[0]); i++) {
525 if (info.device_id == kSupportedDevices[i].pciID) {
526 type = i;
527 *_cookie = index + 1;
528 return B_OK;
533 return B_ENTRY_NOT_FOUND;
537 extern "C" const char**
538 publish_devices(void)
540 TRACE("%s\n", __func__);
541 return (const char**)gDeviceNames;
545 extern "C" status_t
546 init_hardware(void)
548 TRACE("%s\n", __func__);
550 status_t status = get_module(B_PCI_MODULE_NAME, (module_info**)&gPCI);
551 if (status != B_OK) {
552 ERROR("%s: ERROR: pci module unavailable\n", __func__);
553 return status;
556 int32 cookie = 0;
557 uint32 type;
558 pci_info info;
559 status = get_next_radeon_hd(&cookie, info, type);
561 put_module(B_PCI_MODULE_NAME);
562 return status;
566 extern "C" status_t
567 init_driver(void)
569 TRACE("%s\n", __func__);
571 status_t status = get_module(B_PCI_MODULE_NAME, (module_info**)&gPCI);
572 if (status != B_OK) {
573 ERROR("%s: ERROR: pci module unavailable\n", __func__);
574 return status;
577 mutex_init(&gLock, "radeon hd ksync");
579 // find devices
581 int32 found = 0;
583 for (int32 cookie = 0; found < MAX_CARDS;) {
584 pci_info* info = (pci_info*)malloc(sizeof(pci_info));
585 if (info == NULL)
586 break;
588 uint32 type;
589 status = get_next_radeon_hd(&cookie, *info, type);
590 if (status < B_OK) {
591 free(info);
592 break;
595 // create device names & allocate device info structure
597 char name[64];
598 sprintf(name, "graphics/radeon_hd_%02x%02x%02x",
599 info->bus, info->device,
600 info->function);
602 gDeviceNames[found] = strdup(name);
603 if (gDeviceNames[found] == NULL)
604 break;
606 gDeviceInfo[found] = (radeon_info*)malloc(sizeof(radeon_info));
607 if (gDeviceInfo[found] == NULL) {
608 free(gDeviceNames[found]);
609 break;
612 // initialize the structure for later use
614 memset(gDeviceInfo[found], 0, sizeof(radeon_info));
615 gDeviceInfo[found]->init_status = B_NO_INIT;
616 gDeviceInfo[found]->id = found;
617 gDeviceInfo[found]->pci = info;
618 gDeviceInfo[found]->registers = info->u.h0.base_registers[0];
619 gDeviceInfo[found]->pciID = kSupportedDevices[type].pciID;
620 gDeviceInfo[found]->deviceName = kSupportedDevices[type].deviceName;
621 gDeviceInfo[found]->chipsetID = kSupportedDevices[type].chipsetID;
622 gDeviceInfo[found]->dceMajor = kSupportedDevices[type].dceMajor;
623 gDeviceInfo[found]->dceMinor = kSupportedDevices[type].dceMinor;
624 gDeviceInfo[found]->chipsetFlags = kSupportedDevices[type].chipsetFlags;
626 ERROR("%s: GPU(%ld) %s, revision = 0x%x\n", __func__, found,
627 kSupportedDevices[type].deviceName, info->revision);
629 found++;
632 gDeviceNames[found] = NULL;
634 if (found == 0) {
635 mutex_destroy(&gLock);
636 put_module(B_AGP_GART_MODULE_NAME);
637 put_module(B_PCI_MODULE_NAME);
638 ERROR("%s: no supported devices found\n", __func__);
639 return ENODEV;
642 return B_OK;
646 extern "C" void
647 uninit_driver(void)
649 TRACE("%s\n", __func__);
651 mutex_destroy(&gLock);
653 // free device related structures
654 char* name;
655 for (int32 index = 0; (name = gDeviceNames[index]) != NULL; index++) {
656 free(gDeviceInfo[index]);
657 free(name);
660 put_module(B_PCI_MODULE_NAME);
664 extern "C" device_hooks*
665 find_device(const char* name)
667 int index;
669 TRACE("%s\n", __func__);
671 for (index = 0; gDeviceNames[index] != NULL; index++) {
672 if (!strcmp(name, gDeviceNames[index]))
673 return &gDeviceHooks;
676 ERROR("%s: %s wasn't found!\n", __func__, name);
677 return NULL;