blob: 92843461320dea5421ccd226f11cef58e4f746eb [file] [log] [blame]
Alex Deucher0af62b02011-01-06 21:19:31 -05001/*
2 * Copyright 2010 Advanced Micro Devices, Inc.
3 *
4 * Permission is hereby granted, free of charge, to any person obtaining a
5 * copy of this software and associated documentation files (the "Software"),
6 * to deal in the Software without restriction, including without limitation
7 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
8 * and/or sell copies of the Software, and to permit persons to whom the
9 * Software is furnished to do so, subject to the following conditions:
10 *
11 * The above copyright notice and this permission notice shall be included in
12 * all copies or substantial portions of the Software.
13 *
14 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
16 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
17 * THE COPYRIGHT HOLDER(S) OR AUTHOR(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR
18 * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
19 * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
20 * OTHER DEALINGS IN THE SOFTWARE.
21 *
22 * Authors: Alex Deucher
23 */
24#include <linux/firmware.h>
25#include <linux/platform_device.h>
26#include <linux/slab.h>
Paul Gortmakere0cd3602011-08-30 11:04:30 -040027#include <linux/module.h>
David Howells760285e2012-10-02 18:01:07 +010028#include <drm/drmP.h>
Alex Deucher0af62b02011-01-06 21:19:31 -050029#include "radeon.h"
30#include "radeon_asic.h"
David Howells760285e2012-10-02 18:01:07 +010031#include <drm/radeon_drm.h>
Alex Deucher0af62b02011-01-06 21:19:31 -050032#include "nid.h"
33#include "atom.h"
34#include "ni_reg.h"
Alex Deucher0c88a022011-03-02 20:07:31 -050035#include "cayman_blit_shaders.h"
Alex Deucher138e4e12013-01-11 15:33:13 -050036#include "radeon_ucode.h"
Alex Deucher0af62b02011-01-06 21:19:31 -050037
Alex Deucher168757e2013-01-18 19:17:22 -050038extern bool evergreen_is_display_hung(struct radeon_device *rdev);
Alex Deucher187e3592013-01-18 14:51:38 -050039extern void evergreen_print_gpu_status_regs(struct radeon_device *rdev);
Alex Deucherb9952a82011-03-02 20:07:33 -050040extern void evergreen_mc_stop(struct radeon_device *rdev, struct evergreen_mc_save *save);
41extern void evergreen_mc_resume(struct radeon_device *rdev, struct evergreen_mc_save *save);
42extern int evergreen_mc_wait_for_idle(struct radeon_device *rdev);
Alex Deucher755d8192011-03-02 20:07:34 -050043extern void evergreen_mc_program(struct radeon_device *rdev);
44extern void evergreen_irq_suspend(struct radeon_device *rdev);
45extern int evergreen_mc_init(struct radeon_device *rdev);
Alex Deucherd054ac12011-09-01 17:46:15 +000046extern void evergreen_fix_pci_max_read_req_size(struct radeon_device *rdev);
Ilija Hadzicb07759b2011-09-20 10:22:58 -040047extern void evergreen_pcie_gen2_enable(struct radeon_device *rdev);
Alex Deucherc420c742012-03-20 17:18:39 -040048extern void si_rlc_fini(struct radeon_device *rdev);
49extern int si_rlc_init(struct radeon_device *rdev);
Alex Deucherb9952a82011-03-02 20:07:33 -050050
Alex Deucher0af62b02011-01-06 21:19:31 -050051/* Firmware Names */
52MODULE_FIRMWARE("radeon/BARTS_pfp.bin");
53MODULE_FIRMWARE("radeon/BARTS_me.bin");
54MODULE_FIRMWARE("radeon/BARTS_mc.bin");
55MODULE_FIRMWARE("radeon/BTC_rlc.bin");
56MODULE_FIRMWARE("radeon/TURKS_pfp.bin");
57MODULE_FIRMWARE("radeon/TURKS_me.bin");
58MODULE_FIRMWARE("radeon/TURKS_mc.bin");
59MODULE_FIRMWARE("radeon/CAICOS_pfp.bin");
60MODULE_FIRMWARE("radeon/CAICOS_me.bin");
61MODULE_FIRMWARE("radeon/CAICOS_mc.bin");
Alex Deucher9b8253c2011-03-02 20:07:28 -050062MODULE_FIRMWARE("radeon/CAYMAN_pfp.bin");
63MODULE_FIRMWARE("radeon/CAYMAN_me.bin");
64MODULE_FIRMWARE("radeon/CAYMAN_mc.bin");
65MODULE_FIRMWARE("radeon/CAYMAN_rlc.bin");
Alex Deucherc420c742012-03-20 17:18:39 -040066MODULE_FIRMWARE("radeon/ARUBA_pfp.bin");
67MODULE_FIRMWARE("radeon/ARUBA_me.bin");
68MODULE_FIRMWARE("radeon/ARUBA_rlc.bin");
Alex Deucher0af62b02011-01-06 21:19:31 -050069
Alex Deuchera2c96a22013-02-28 17:58:36 -050070
71static const u32 cayman_golden_registers2[] =
72{
73 0x3e5c, 0xffffffff, 0x00000000,
74 0x3e48, 0xffffffff, 0x00000000,
75 0x3e4c, 0xffffffff, 0x00000000,
76 0x3e64, 0xffffffff, 0x00000000,
77 0x3e50, 0xffffffff, 0x00000000,
78 0x3e60, 0xffffffff, 0x00000000
79};
80
81static const u32 cayman_golden_registers[] =
82{
83 0x5eb4, 0xffffffff, 0x00000002,
84 0x5e78, 0x8f311ff1, 0x001000f0,
85 0x3f90, 0xffff0000, 0xff000000,
86 0x9148, 0xffff0000, 0xff000000,
87 0x3f94, 0xffff0000, 0xff000000,
88 0x914c, 0xffff0000, 0xff000000,
89 0xc78, 0x00000080, 0x00000080,
90 0xbd4, 0x70073777, 0x00011003,
91 0xd02c, 0xbfffff1f, 0x08421000,
92 0xd0b8, 0x73773777, 0x02011003,
93 0x5bc0, 0x00200000, 0x50100000,
94 0x98f8, 0x33773777, 0x02011003,
95 0x98fc, 0xffffffff, 0x76541032,
96 0x7030, 0x31000311, 0x00000011,
97 0x2f48, 0x33773777, 0x42010001,
98 0x6b28, 0x00000010, 0x00000012,
99 0x7728, 0x00000010, 0x00000012,
100 0x10328, 0x00000010, 0x00000012,
101 0x10f28, 0x00000010, 0x00000012,
102 0x11b28, 0x00000010, 0x00000012,
103 0x12728, 0x00000010, 0x00000012,
104 0x240c, 0x000007ff, 0x00000000,
105 0x8a14, 0xf000001f, 0x00000007,
106 0x8b24, 0x3fff3fff, 0x00ff0fff,
107 0x8b10, 0x0000ff0f, 0x00000000,
108 0x28a4c, 0x07ffffff, 0x06000000,
109 0x10c, 0x00000001, 0x00010003,
110 0xa02c, 0xffffffff, 0x0000009b,
111 0x913c, 0x0000010f, 0x01000100,
112 0x8c04, 0xf8ff00ff, 0x40600060,
113 0x28350, 0x00000f01, 0x00000000,
114 0x9508, 0x3700001f, 0x00000002,
115 0x960c, 0xffffffff, 0x54763210,
116 0x88c4, 0x001f3ae3, 0x00000082,
117 0x88d0, 0xffffffff, 0x0f40df40,
118 0x88d4, 0x0000001f, 0x00000010,
119 0x8974, 0xffffffff, 0x00000000
120};
121
122static const u32 dvst_golden_registers2[] =
123{
124 0x8f8, 0xffffffff, 0,
125 0x8fc, 0x00380000, 0,
126 0x8f8, 0xffffffff, 1,
127 0x8fc, 0x0e000000, 0
128};
129
130static const u32 dvst_golden_registers[] =
131{
132 0x690, 0x3fff3fff, 0x20c00033,
133 0x918c, 0x0fff0fff, 0x00010006,
134 0x91a8, 0x0fff0fff, 0x00010006,
135 0x9150, 0xffffdfff, 0x6e944040,
136 0x917c, 0x0fff0fff, 0x00030002,
137 0x9198, 0x0fff0fff, 0x00030002,
138 0x915c, 0x0fff0fff, 0x00010000,
139 0x3f90, 0xffff0001, 0xff000000,
140 0x9178, 0x0fff0fff, 0x00070000,
141 0x9194, 0x0fff0fff, 0x00070000,
142 0x9148, 0xffff0001, 0xff000000,
143 0x9190, 0x0fff0fff, 0x00090008,
144 0x91ac, 0x0fff0fff, 0x00090008,
145 0x3f94, 0xffff0000, 0xff000000,
146 0x914c, 0xffff0000, 0xff000000,
147 0x929c, 0x00000fff, 0x00000001,
148 0x55e4, 0xff607fff, 0xfc000100,
149 0x8a18, 0xff000fff, 0x00000100,
150 0x8b28, 0xff000fff, 0x00000100,
151 0x9144, 0xfffc0fff, 0x00000100,
152 0x6ed8, 0x00010101, 0x00010000,
153 0x9830, 0xffffffff, 0x00000000,
154 0x9834, 0xf00fffff, 0x00000400,
155 0x9838, 0xfffffffe, 0x00000000,
156 0xd0c0, 0xff000fff, 0x00000100,
157 0xd02c, 0xbfffff1f, 0x08421000,
158 0xd0b8, 0x73773777, 0x12010001,
159 0x5bb0, 0x000000f0, 0x00000070,
160 0x98f8, 0x73773777, 0x12010001,
161 0x98fc, 0xffffffff, 0x00000010,
162 0x9b7c, 0x00ff0000, 0x00fc0000,
163 0x8030, 0x00001f0f, 0x0000100a,
164 0x2f48, 0x73773777, 0x12010001,
165 0x2408, 0x00030000, 0x000c007f,
166 0x8a14, 0xf000003f, 0x00000007,
167 0x8b24, 0x3fff3fff, 0x00ff0fff,
168 0x8b10, 0x0000ff0f, 0x00000000,
169 0x28a4c, 0x07ffffff, 0x06000000,
170 0x4d8, 0x00000fff, 0x00000100,
171 0xa008, 0xffffffff, 0x00010000,
172 0x913c, 0xffff03ff, 0x01000100,
173 0x8c00, 0x000000ff, 0x00000003,
174 0x8c04, 0xf8ff00ff, 0x40600060,
175 0x8cf0, 0x1fff1fff, 0x08e00410,
176 0x28350, 0x00000f01, 0x00000000,
177 0x9508, 0xf700071f, 0x00000002,
178 0x960c, 0xffffffff, 0x54763210,
179 0x20ef8, 0x01ff01ff, 0x00000002,
180 0x20e98, 0xfffffbff, 0x00200000,
181 0x2015c, 0xffffffff, 0x00000f40,
182 0x88c4, 0x001f3ae3, 0x00000082,
183 0x8978, 0x3fffffff, 0x04050140,
184 0x88d4, 0x0000001f, 0x00000010,
185 0x8974, 0xffffffff, 0x00000000
186};
187
188static const u32 scrapper_golden_registers[] =
189{
190 0x690, 0x3fff3fff, 0x20c00033,
191 0x918c, 0x0fff0fff, 0x00010006,
192 0x918c, 0x0fff0fff, 0x00010006,
193 0x91a8, 0x0fff0fff, 0x00010006,
194 0x91a8, 0x0fff0fff, 0x00010006,
195 0x9150, 0xffffdfff, 0x6e944040,
196 0x9150, 0xffffdfff, 0x6e944040,
197 0x917c, 0x0fff0fff, 0x00030002,
198 0x917c, 0x0fff0fff, 0x00030002,
199 0x9198, 0x0fff0fff, 0x00030002,
200 0x9198, 0x0fff0fff, 0x00030002,
201 0x915c, 0x0fff0fff, 0x00010000,
202 0x915c, 0x0fff0fff, 0x00010000,
203 0x3f90, 0xffff0001, 0xff000000,
204 0x3f90, 0xffff0001, 0xff000000,
205 0x9178, 0x0fff0fff, 0x00070000,
206 0x9178, 0x0fff0fff, 0x00070000,
207 0x9194, 0x0fff0fff, 0x00070000,
208 0x9194, 0x0fff0fff, 0x00070000,
209 0x9148, 0xffff0001, 0xff000000,
210 0x9148, 0xffff0001, 0xff000000,
211 0x9190, 0x0fff0fff, 0x00090008,
212 0x9190, 0x0fff0fff, 0x00090008,
213 0x91ac, 0x0fff0fff, 0x00090008,
214 0x91ac, 0x0fff0fff, 0x00090008,
215 0x3f94, 0xffff0000, 0xff000000,
216 0x3f94, 0xffff0000, 0xff000000,
217 0x914c, 0xffff0000, 0xff000000,
218 0x914c, 0xffff0000, 0xff000000,
219 0x929c, 0x00000fff, 0x00000001,
220 0x929c, 0x00000fff, 0x00000001,
221 0x55e4, 0xff607fff, 0xfc000100,
222 0x8a18, 0xff000fff, 0x00000100,
223 0x8a18, 0xff000fff, 0x00000100,
224 0x8b28, 0xff000fff, 0x00000100,
225 0x8b28, 0xff000fff, 0x00000100,
226 0x9144, 0xfffc0fff, 0x00000100,
227 0x9144, 0xfffc0fff, 0x00000100,
228 0x6ed8, 0x00010101, 0x00010000,
229 0x9830, 0xffffffff, 0x00000000,
230 0x9830, 0xffffffff, 0x00000000,
231 0x9834, 0xf00fffff, 0x00000400,
232 0x9834, 0xf00fffff, 0x00000400,
233 0x9838, 0xfffffffe, 0x00000000,
234 0x9838, 0xfffffffe, 0x00000000,
235 0xd0c0, 0xff000fff, 0x00000100,
236 0xd02c, 0xbfffff1f, 0x08421000,
237 0xd02c, 0xbfffff1f, 0x08421000,
238 0xd0b8, 0x73773777, 0x12010001,
239 0xd0b8, 0x73773777, 0x12010001,
240 0x5bb0, 0x000000f0, 0x00000070,
241 0x98f8, 0x73773777, 0x12010001,
242 0x98f8, 0x73773777, 0x12010001,
243 0x98fc, 0xffffffff, 0x00000010,
244 0x98fc, 0xffffffff, 0x00000010,
245 0x9b7c, 0x00ff0000, 0x00fc0000,
246 0x9b7c, 0x00ff0000, 0x00fc0000,
247 0x8030, 0x00001f0f, 0x0000100a,
248 0x8030, 0x00001f0f, 0x0000100a,
249 0x2f48, 0x73773777, 0x12010001,
250 0x2f48, 0x73773777, 0x12010001,
251 0x2408, 0x00030000, 0x000c007f,
252 0x8a14, 0xf000003f, 0x00000007,
253 0x8a14, 0xf000003f, 0x00000007,
254 0x8b24, 0x3fff3fff, 0x00ff0fff,
255 0x8b24, 0x3fff3fff, 0x00ff0fff,
256 0x8b10, 0x0000ff0f, 0x00000000,
257 0x8b10, 0x0000ff0f, 0x00000000,
258 0x28a4c, 0x07ffffff, 0x06000000,
259 0x28a4c, 0x07ffffff, 0x06000000,
260 0x4d8, 0x00000fff, 0x00000100,
261 0x4d8, 0x00000fff, 0x00000100,
262 0xa008, 0xffffffff, 0x00010000,
263 0xa008, 0xffffffff, 0x00010000,
264 0x913c, 0xffff03ff, 0x01000100,
265 0x913c, 0xffff03ff, 0x01000100,
266 0x90e8, 0x001fffff, 0x010400c0,
267 0x8c00, 0x000000ff, 0x00000003,
268 0x8c00, 0x000000ff, 0x00000003,
269 0x8c04, 0xf8ff00ff, 0x40600060,
270 0x8c04, 0xf8ff00ff, 0x40600060,
271 0x8c30, 0x0000000f, 0x00040005,
272 0x8cf0, 0x1fff1fff, 0x08e00410,
273 0x8cf0, 0x1fff1fff, 0x08e00410,
274 0x900c, 0x00ffffff, 0x0017071f,
275 0x28350, 0x00000f01, 0x00000000,
276 0x28350, 0x00000f01, 0x00000000,
277 0x9508, 0xf700071f, 0x00000002,
278 0x9508, 0xf700071f, 0x00000002,
279 0x9688, 0x00300000, 0x0017000f,
280 0x960c, 0xffffffff, 0x54763210,
281 0x960c, 0xffffffff, 0x54763210,
282 0x20ef8, 0x01ff01ff, 0x00000002,
283 0x20e98, 0xfffffbff, 0x00200000,
284 0x2015c, 0xffffffff, 0x00000f40,
285 0x88c4, 0x001f3ae3, 0x00000082,
286 0x88c4, 0x001f3ae3, 0x00000082,
287 0x8978, 0x3fffffff, 0x04050140,
288 0x8978, 0x3fffffff, 0x04050140,
289 0x88d4, 0x0000001f, 0x00000010,
290 0x88d4, 0x0000001f, 0x00000010,
291 0x8974, 0xffffffff, 0x00000000,
292 0x8974, 0xffffffff, 0x00000000
293};
294
295static void ni_init_golden_registers(struct radeon_device *rdev)
296{
297 switch (rdev->family) {
298 case CHIP_CAYMAN:
299 radeon_program_register_sequence(rdev,
300 cayman_golden_registers,
301 (const u32)ARRAY_SIZE(cayman_golden_registers));
302 radeon_program_register_sequence(rdev,
303 cayman_golden_registers2,
304 (const u32)ARRAY_SIZE(cayman_golden_registers2));
305 break;
306 case CHIP_ARUBA:
307 if ((rdev->pdev->device == 0x9900) ||
308 (rdev->pdev->device == 0x9901) ||
309 (rdev->pdev->device == 0x9903) ||
310 (rdev->pdev->device == 0x9904) ||
311 (rdev->pdev->device == 0x9905) ||
312 (rdev->pdev->device == 0x9906) ||
313 (rdev->pdev->device == 0x9907) ||
314 (rdev->pdev->device == 0x9908) ||
315 (rdev->pdev->device == 0x9909) ||
316 (rdev->pdev->device == 0x990A) ||
317 (rdev->pdev->device == 0x990B) ||
318 (rdev->pdev->device == 0x990C) ||
319 (rdev->pdev->device == 0x990D) ||
320 (rdev->pdev->device == 0x990E) ||
321 (rdev->pdev->device == 0x990F) ||
322 (rdev->pdev->device == 0x9910) ||
323 (rdev->pdev->device == 0x9913) ||
324 (rdev->pdev->device == 0x9917) ||
325 (rdev->pdev->device == 0x9918)) {
326 radeon_program_register_sequence(rdev,
327 dvst_golden_registers,
328 (const u32)ARRAY_SIZE(dvst_golden_registers));
329 radeon_program_register_sequence(rdev,
330 dvst_golden_registers2,
331 (const u32)ARRAY_SIZE(dvst_golden_registers2));
332 } else {
333 radeon_program_register_sequence(rdev,
334 scrapper_golden_registers,
335 (const u32)ARRAY_SIZE(scrapper_golden_registers));
336 radeon_program_register_sequence(rdev,
337 dvst_golden_registers2,
338 (const u32)ARRAY_SIZE(dvst_golden_registers2));
339 }
340 break;
341 default:
342 break;
343 }
344}
345
Alex Deucher0af62b02011-01-06 21:19:31 -0500346#define BTC_IO_MC_REGS_SIZE 29
347
348static const u32 barts_io_mc_regs[BTC_IO_MC_REGS_SIZE][2] = {
349 {0x00000077, 0xff010100},
350 {0x00000078, 0x00000000},
351 {0x00000079, 0x00001434},
352 {0x0000007a, 0xcc08ec08},
353 {0x0000007b, 0x00040000},
354 {0x0000007c, 0x000080c0},
355 {0x0000007d, 0x09000000},
356 {0x0000007e, 0x00210404},
357 {0x00000081, 0x08a8e800},
358 {0x00000082, 0x00030444},
359 {0x00000083, 0x00000000},
360 {0x00000085, 0x00000001},
361 {0x00000086, 0x00000002},
362 {0x00000087, 0x48490000},
363 {0x00000088, 0x20244647},
364 {0x00000089, 0x00000005},
365 {0x0000008b, 0x66030000},
366 {0x0000008c, 0x00006603},
367 {0x0000008d, 0x00000100},
368 {0x0000008f, 0x00001c0a},
369 {0x00000090, 0xff000001},
370 {0x00000094, 0x00101101},
371 {0x00000095, 0x00000fff},
372 {0x00000096, 0x00116fff},
373 {0x00000097, 0x60010000},
374 {0x00000098, 0x10010000},
375 {0x00000099, 0x00006000},
376 {0x0000009a, 0x00001000},
377 {0x0000009f, 0x00946a00}
378};
379
380static const u32 turks_io_mc_regs[BTC_IO_MC_REGS_SIZE][2] = {
381 {0x00000077, 0xff010100},
382 {0x00000078, 0x00000000},
383 {0x00000079, 0x00001434},
384 {0x0000007a, 0xcc08ec08},
385 {0x0000007b, 0x00040000},
386 {0x0000007c, 0x000080c0},
387 {0x0000007d, 0x09000000},
388 {0x0000007e, 0x00210404},
389 {0x00000081, 0x08a8e800},
390 {0x00000082, 0x00030444},
391 {0x00000083, 0x00000000},
392 {0x00000085, 0x00000001},
393 {0x00000086, 0x00000002},
394 {0x00000087, 0x48490000},
395 {0x00000088, 0x20244647},
396 {0x00000089, 0x00000005},
397 {0x0000008b, 0x66030000},
398 {0x0000008c, 0x00006603},
399 {0x0000008d, 0x00000100},
400 {0x0000008f, 0x00001c0a},
401 {0x00000090, 0xff000001},
402 {0x00000094, 0x00101101},
403 {0x00000095, 0x00000fff},
404 {0x00000096, 0x00116fff},
405 {0x00000097, 0x60010000},
406 {0x00000098, 0x10010000},
407 {0x00000099, 0x00006000},
408 {0x0000009a, 0x00001000},
409 {0x0000009f, 0x00936a00}
410};
411
412static const u32 caicos_io_mc_regs[BTC_IO_MC_REGS_SIZE][2] = {
413 {0x00000077, 0xff010100},
414 {0x00000078, 0x00000000},
415 {0x00000079, 0x00001434},
416 {0x0000007a, 0xcc08ec08},
417 {0x0000007b, 0x00040000},
418 {0x0000007c, 0x000080c0},
419 {0x0000007d, 0x09000000},
420 {0x0000007e, 0x00210404},
421 {0x00000081, 0x08a8e800},
422 {0x00000082, 0x00030444},
423 {0x00000083, 0x00000000},
424 {0x00000085, 0x00000001},
425 {0x00000086, 0x00000002},
426 {0x00000087, 0x48490000},
427 {0x00000088, 0x20244647},
428 {0x00000089, 0x00000005},
429 {0x0000008b, 0x66030000},
430 {0x0000008c, 0x00006603},
431 {0x0000008d, 0x00000100},
432 {0x0000008f, 0x00001c0a},
433 {0x00000090, 0xff000001},
434 {0x00000094, 0x00101101},
435 {0x00000095, 0x00000fff},
436 {0x00000096, 0x00116fff},
437 {0x00000097, 0x60010000},
438 {0x00000098, 0x10010000},
439 {0x00000099, 0x00006000},
440 {0x0000009a, 0x00001000},
441 {0x0000009f, 0x00916a00}
442};
443
Alex Deucher9b8253c2011-03-02 20:07:28 -0500444static const u32 cayman_io_mc_regs[BTC_IO_MC_REGS_SIZE][2] = {
445 {0x00000077, 0xff010100},
446 {0x00000078, 0x00000000},
447 {0x00000079, 0x00001434},
448 {0x0000007a, 0xcc08ec08},
449 {0x0000007b, 0x00040000},
450 {0x0000007c, 0x000080c0},
451 {0x0000007d, 0x09000000},
452 {0x0000007e, 0x00210404},
453 {0x00000081, 0x08a8e800},
454 {0x00000082, 0x00030444},
455 {0x00000083, 0x00000000},
456 {0x00000085, 0x00000001},
457 {0x00000086, 0x00000002},
458 {0x00000087, 0x48490000},
459 {0x00000088, 0x20244647},
460 {0x00000089, 0x00000005},
461 {0x0000008b, 0x66030000},
462 {0x0000008c, 0x00006603},
463 {0x0000008d, 0x00000100},
464 {0x0000008f, 0x00001c0a},
465 {0x00000090, 0xff000001},
466 {0x00000094, 0x00101101},
467 {0x00000095, 0x00000fff},
468 {0x00000096, 0x00116fff},
469 {0x00000097, 0x60010000},
470 {0x00000098, 0x10010000},
471 {0x00000099, 0x00006000},
472 {0x0000009a, 0x00001000},
473 {0x0000009f, 0x00976b00}
474};
475
Alex Deucher755d8192011-03-02 20:07:34 -0500476int ni_mc_load_microcode(struct radeon_device *rdev)
Alex Deucher0af62b02011-01-06 21:19:31 -0500477{
478 const __be32 *fw_data;
479 u32 mem_type, running, blackout = 0;
480 u32 *io_mc_regs;
Alex Deucher9b8253c2011-03-02 20:07:28 -0500481 int i, ucode_size, regs_size;
Alex Deucher0af62b02011-01-06 21:19:31 -0500482
483 if (!rdev->mc_fw)
484 return -EINVAL;
485
486 switch (rdev->family) {
487 case CHIP_BARTS:
488 io_mc_regs = (u32 *)&barts_io_mc_regs;
Alex Deucher9b8253c2011-03-02 20:07:28 -0500489 ucode_size = BTC_MC_UCODE_SIZE;
490 regs_size = BTC_IO_MC_REGS_SIZE;
Alex Deucher0af62b02011-01-06 21:19:31 -0500491 break;
492 case CHIP_TURKS:
493 io_mc_regs = (u32 *)&turks_io_mc_regs;
Alex Deucher9b8253c2011-03-02 20:07:28 -0500494 ucode_size = BTC_MC_UCODE_SIZE;
495 regs_size = BTC_IO_MC_REGS_SIZE;
Alex Deucher0af62b02011-01-06 21:19:31 -0500496 break;
497 case CHIP_CAICOS:
498 default:
499 io_mc_regs = (u32 *)&caicos_io_mc_regs;
Alex Deucher9b8253c2011-03-02 20:07:28 -0500500 ucode_size = BTC_MC_UCODE_SIZE;
501 regs_size = BTC_IO_MC_REGS_SIZE;
502 break;
503 case CHIP_CAYMAN:
504 io_mc_regs = (u32 *)&cayman_io_mc_regs;
505 ucode_size = CAYMAN_MC_UCODE_SIZE;
506 regs_size = BTC_IO_MC_REGS_SIZE;
Alex Deucher0af62b02011-01-06 21:19:31 -0500507 break;
508 }
509
510 mem_type = (RREG32(MC_SEQ_MISC0) & MC_SEQ_MISC0_GDDR5_MASK) >> MC_SEQ_MISC0_GDDR5_SHIFT;
511 running = RREG32(MC_SEQ_SUP_CNTL) & RUN_MASK;
512
513 if ((mem_type == MC_SEQ_MISC0_GDDR5_VALUE) && (running == 0)) {
514 if (running) {
515 blackout = RREG32(MC_SHARED_BLACKOUT_CNTL);
516 WREG32(MC_SHARED_BLACKOUT_CNTL, 1);
517 }
518
519 /* reset the engine and set to writable */
520 WREG32(MC_SEQ_SUP_CNTL, 0x00000008);
521 WREG32(MC_SEQ_SUP_CNTL, 0x00000010);
522
523 /* load mc io regs */
Alex Deucher9b8253c2011-03-02 20:07:28 -0500524 for (i = 0; i < regs_size; i++) {
Alex Deucher0af62b02011-01-06 21:19:31 -0500525 WREG32(MC_SEQ_IO_DEBUG_INDEX, io_mc_regs[(i << 1)]);
526 WREG32(MC_SEQ_IO_DEBUG_DATA, io_mc_regs[(i << 1) + 1]);
527 }
528 /* load the MC ucode */
529 fw_data = (const __be32 *)rdev->mc_fw->data;
Alex Deucher9b8253c2011-03-02 20:07:28 -0500530 for (i = 0; i < ucode_size; i++)
Alex Deucher0af62b02011-01-06 21:19:31 -0500531 WREG32(MC_SEQ_SUP_PGM, be32_to_cpup(fw_data++));
532
533 /* put the engine back into the active state */
534 WREG32(MC_SEQ_SUP_CNTL, 0x00000008);
535 WREG32(MC_SEQ_SUP_CNTL, 0x00000004);
536 WREG32(MC_SEQ_SUP_CNTL, 0x00000001);
537
538 /* wait for training to complete */
Alex Deucher0e2c9782011-11-02 18:08:25 -0400539 for (i = 0; i < rdev->usec_timeout; i++) {
540 if (RREG32(MC_IO_PAD_CNTL_D0) & MEM_FALL_OUT_CMD)
541 break;
542 udelay(1);
543 }
Alex Deucher0af62b02011-01-06 21:19:31 -0500544
545 if (running)
546 WREG32(MC_SHARED_BLACKOUT_CNTL, blackout);
547 }
548
549 return 0;
550}
551
552int ni_init_microcode(struct radeon_device *rdev)
553{
554 struct platform_device *pdev;
555 const char *chip_name;
556 const char *rlc_chip_name;
557 size_t pfp_req_size, me_req_size, rlc_req_size, mc_req_size;
558 char fw_name[30];
559 int err;
560
561 DRM_DEBUG("\n");
562
563 pdev = platform_device_register_simple("radeon_cp", 0, NULL, 0);
564 err = IS_ERR(pdev);
565 if (err) {
566 printk(KERN_ERR "radeon_cp: Failed to register firmware\n");
567 return -EINVAL;
568 }
569
570 switch (rdev->family) {
571 case CHIP_BARTS:
572 chip_name = "BARTS";
573 rlc_chip_name = "BTC";
Alex Deucher9b8253c2011-03-02 20:07:28 -0500574 pfp_req_size = EVERGREEN_PFP_UCODE_SIZE * 4;
575 me_req_size = EVERGREEN_PM4_UCODE_SIZE * 4;
576 rlc_req_size = EVERGREEN_RLC_UCODE_SIZE * 4;
577 mc_req_size = BTC_MC_UCODE_SIZE * 4;
Alex Deucher0af62b02011-01-06 21:19:31 -0500578 break;
579 case CHIP_TURKS:
580 chip_name = "TURKS";
581 rlc_chip_name = "BTC";
Alex Deucher9b8253c2011-03-02 20:07:28 -0500582 pfp_req_size = EVERGREEN_PFP_UCODE_SIZE * 4;
583 me_req_size = EVERGREEN_PM4_UCODE_SIZE * 4;
584 rlc_req_size = EVERGREEN_RLC_UCODE_SIZE * 4;
585 mc_req_size = BTC_MC_UCODE_SIZE * 4;
Alex Deucher0af62b02011-01-06 21:19:31 -0500586 break;
587 case CHIP_CAICOS:
588 chip_name = "CAICOS";
589 rlc_chip_name = "BTC";
Alex Deucher9b8253c2011-03-02 20:07:28 -0500590 pfp_req_size = EVERGREEN_PFP_UCODE_SIZE * 4;
591 me_req_size = EVERGREEN_PM4_UCODE_SIZE * 4;
592 rlc_req_size = EVERGREEN_RLC_UCODE_SIZE * 4;
593 mc_req_size = BTC_MC_UCODE_SIZE * 4;
594 break;
595 case CHIP_CAYMAN:
596 chip_name = "CAYMAN";
597 rlc_chip_name = "CAYMAN";
598 pfp_req_size = CAYMAN_PFP_UCODE_SIZE * 4;
599 me_req_size = CAYMAN_PM4_UCODE_SIZE * 4;
600 rlc_req_size = CAYMAN_RLC_UCODE_SIZE * 4;
601 mc_req_size = CAYMAN_MC_UCODE_SIZE * 4;
Alex Deucher0af62b02011-01-06 21:19:31 -0500602 break;
Alex Deucherc420c742012-03-20 17:18:39 -0400603 case CHIP_ARUBA:
604 chip_name = "ARUBA";
605 rlc_chip_name = "ARUBA";
606 /* pfp/me same size as CAYMAN */
607 pfp_req_size = CAYMAN_PFP_UCODE_SIZE * 4;
608 me_req_size = CAYMAN_PM4_UCODE_SIZE * 4;
609 rlc_req_size = ARUBA_RLC_UCODE_SIZE * 4;
610 mc_req_size = 0;
611 break;
Alex Deucher0af62b02011-01-06 21:19:31 -0500612 default: BUG();
613 }
614
Alex Deucher0af62b02011-01-06 21:19:31 -0500615 DRM_INFO("Loading %s Microcode\n", chip_name);
616
617 snprintf(fw_name, sizeof(fw_name), "radeon/%s_pfp.bin", chip_name);
618 err = request_firmware(&rdev->pfp_fw, fw_name, &pdev->dev);
619 if (err)
620 goto out;
621 if (rdev->pfp_fw->size != pfp_req_size) {
622 printk(KERN_ERR
623 "ni_cp: Bogus length %zu in firmware \"%s\"\n",
624 rdev->pfp_fw->size, fw_name);
625 err = -EINVAL;
626 goto out;
627 }
628
629 snprintf(fw_name, sizeof(fw_name), "radeon/%s_me.bin", chip_name);
630 err = request_firmware(&rdev->me_fw, fw_name, &pdev->dev);
631 if (err)
632 goto out;
633 if (rdev->me_fw->size != me_req_size) {
634 printk(KERN_ERR
635 "ni_cp: Bogus length %zu in firmware \"%s\"\n",
636 rdev->me_fw->size, fw_name);
637 err = -EINVAL;
638 }
639
640 snprintf(fw_name, sizeof(fw_name), "radeon/%s_rlc.bin", rlc_chip_name);
641 err = request_firmware(&rdev->rlc_fw, fw_name, &pdev->dev);
642 if (err)
643 goto out;
644 if (rdev->rlc_fw->size != rlc_req_size) {
645 printk(KERN_ERR
646 "ni_rlc: Bogus length %zu in firmware \"%s\"\n",
647 rdev->rlc_fw->size, fw_name);
648 err = -EINVAL;
649 }
650
Alex Deucherc420c742012-03-20 17:18:39 -0400651 /* no MC ucode on TN */
652 if (!(rdev->flags & RADEON_IS_IGP)) {
653 snprintf(fw_name, sizeof(fw_name), "radeon/%s_mc.bin", chip_name);
654 err = request_firmware(&rdev->mc_fw, fw_name, &pdev->dev);
655 if (err)
656 goto out;
657 if (rdev->mc_fw->size != mc_req_size) {
658 printk(KERN_ERR
659 "ni_mc: Bogus length %zu in firmware \"%s\"\n",
660 rdev->mc_fw->size, fw_name);
661 err = -EINVAL;
662 }
Alex Deucher0af62b02011-01-06 21:19:31 -0500663 }
664out:
665 platform_device_unregister(pdev);
666
667 if (err) {
668 if (err != -EINVAL)
669 printk(KERN_ERR
670 "ni_cp: Failed to load firmware \"%s\"\n",
671 fw_name);
672 release_firmware(rdev->pfp_fw);
673 rdev->pfp_fw = NULL;
674 release_firmware(rdev->me_fw);
675 rdev->me_fw = NULL;
676 release_firmware(rdev->rlc_fw);
677 rdev->rlc_fw = NULL;
678 release_firmware(rdev->mc_fw);
679 rdev->mc_fw = NULL;
680 }
681 return err;
682}
683
Alex Deucher29a15222012-12-14 11:57:36 -0500684int tn_get_temp(struct radeon_device *rdev)
685{
686 u32 temp = RREG32_SMC(TN_CURRENT_GNB_TEMP) & 0x7ff;
687 int actual_temp = (temp / 8) - 49;
688
689 return actual_temp * 1000;
690}
691
Alex Deucherfecf1d02011-03-02 20:07:29 -0500692/*
693 * Core functions
694 */
Alex Deucherfecf1d02011-03-02 20:07:29 -0500695static void cayman_gpu_init(struct radeon_device *rdev)
696{
Alex Deucherfecf1d02011-03-02 20:07:29 -0500697 u32 gb_addr_config = 0;
698 u32 mc_shared_chmap, mc_arb_ramcfg;
Alex Deucherfecf1d02011-03-02 20:07:29 -0500699 u32 cgts_tcc_disable;
700 u32 sx_debug_1;
701 u32 smx_dc_ctl0;
Alex Deucherfecf1d02011-03-02 20:07:29 -0500702 u32 cgts_sm_ctrl_reg;
703 u32 hdp_host_path_cntl;
704 u32 tmp;
Alex Deucher416a2bd2012-05-31 19:00:25 -0400705 u32 disabled_rb_mask;
Alex Deucherfecf1d02011-03-02 20:07:29 -0500706 int i, j;
707
708 switch (rdev->family) {
709 case CHIP_CAYMAN:
Alex Deucherfecf1d02011-03-02 20:07:29 -0500710 rdev->config.cayman.max_shader_engines = 2;
711 rdev->config.cayman.max_pipes_per_simd = 4;
712 rdev->config.cayman.max_tile_pipes = 8;
713 rdev->config.cayman.max_simds_per_se = 12;
714 rdev->config.cayman.max_backends_per_se = 4;
715 rdev->config.cayman.max_texture_channel_caches = 8;
716 rdev->config.cayman.max_gprs = 256;
717 rdev->config.cayman.max_threads = 256;
718 rdev->config.cayman.max_gs_threads = 32;
719 rdev->config.cayman.max_stack_entries = 512;
720 rdev->config.cayman.sx_num_of_sets = 8;
721 rdev->config.cayman.sx_max_export_size = 256;
722 rdev->config.cayman.sx_max_export_pos_size = 64;
723 rdev->config.cayman.sx_max_export_smx_size = 192;
724 rdev->config.cayman.max_hw_contexts = 8;
725 rdev->config.cayman.sq_num_cf_insts = 2;
726
727 rdev->config.cayman.sc_prim_fifo_size = 0x100;
728 rdev->config.cayman.sc_hiz_tile_fifo_size = 0x30;
729 rdev->config.cayman.sc_earlyz_tile_fifo_size = 0x130;
Alex Deucher416a2bd2012-05-31 19:00:25 -0400730 gb_addr_config = CAYMAN_GB_ADDR_CONFIG_GOLDEN;
Alex Deucherfecf1d02011-03-02 20:07:29 -0500731 break;
Alex Deucher7b76e472012-03-20 17:18:36 -0400732 case CHIP_ARUBA:
733 default:
734 rdev->config.cayman.max_shader_engines = 1;
735 rdev->config.cayman.max_pipes_per_simd = 4;
736 rdev->config.cayman.max_tile_pipes = 2;
737 if ((rdev->pdev->device == 0x9900) ||
Alex Deucherd430f7d2012-06-05 09:50:28 -0400738 (rdev->pdev->device == 0x9901) ||
739 (rdev->pdev->device == 0x9905) ||
740 (rdev->pdev->device == 0x9906) ||
741 (rdev->pdev->device == 0x9907) ||
742 (rdev->pdev->device == 0x9908) ||
743 (rdev->pdev->device == 0x9909) ||
Alex Deuchere4d17062013-03-08 13:44:15 -0500744 (rdev->pdev->device == 0x990B) ||
745 (rdev->pdev->device == 0x990C) ||
746 (rdev->pdev->device == 0x990F) ||
Alex Deucherd430f7d2012-06-05 09:50:28 -0400747 (rdev->pdev->device == 0x9910) ||
Alex Deuchere4d17062013-03-08 13:44:15 -0500748 (rdev->pdev->device == 0x9917) ||
Alex Deucher62d1f922013-04-25 14:06:05 -0400749 (rdev->pdev->device == 0x9999) ||
750 (rdev->pdev->device == 0x999C)) {
Alex Deucher7b76e472012-03-20 17:18:36 -0400751 rdev->config.cayman.max_simds_per_se = 6;
752 rdev->config.cayman.max_backends_per_se = 2;
753 } else if ((rdev->pdev->device == 0x9903) ||
Alex Deucherd430f7d2012-06-05 09:50:28 -0400754 (rdev->pdev->device == 0x9904) ||
755 (rdev->pdev->device == 0x990A) ||
Alex Deuchere4d17062013-03-08 13:44:15 -0500756 (rdev->pdev->device == 0x990D) ||
757 (rdev->pdev->device == 0x990E) ||
Alex Deucherd430f7d2012-06-05 09:50:28 -0400758 (rdev->pdev->device == 0x9913) ||
Alex Deucher62d1f922013-04-25 14:06:05 -0400759 (rdev->pdev->device == 0x9918) ||
760 (rdev->pdev->device == 0x999D)) {
Alex Deucher7b76e472012-03-20 17:18:36 -0400761 rdev->config.cayman.max_simds_per_se = 4;
762 rdev->config.cayman.max_backends_per_se = 2;
Alex Deucherd430f7d2012-06-05 09:50:28 -0400763 } else if ((rdev->pdev->device == 0x9919) ||
764 (rdev->pdev->device == 0x9990) ||
765 (rdev->pdev->device == 0x9991) ||
766 (rdev->pdev->device == 0x9994) ||
Alex Deuchere4d17062013-03-08 13:44:15 -0500767 (rdev->pdev->device == 0x9995) ||
768 (rdev->pdev->device == 0x9996) ||
769 (rdev->pdev->device == 0x999A) ||
Alex Deucherd430f7d2012-06-05 09:50:28 -0400770 (rdev->pdev->device == 0x99A0)) {
Alex Deucher7b76e472012-03-20 17:18:36 -0400771 rdev->config.cayman.max_simds_per_se = 3;
772 rdev->config.cayman.max_backends_per_se = 1;
773 } else {
774 rdev->config.cayman.max_simds_per_se = 2;
775 rdev->config.cayman.max_backends_per_se = 1;
776 }
777 rdev->config.cayman.max_texture_channel_caches = 2;
778 rdev->config.cayman.max_gprs = 256;
779 rdev->config.cayman.max_threads = 256;
780 rdev->config.cayman.max_gs_threads = 32;
781 rdev->config.cayman.max_stack_entries = 512;
782 rdev->config.cayman.sx_num_of_sets = 8;
783 rdev->config.cayman.sx_max_export_size = 256;
784 rdev->config.cayman.sx_max_export_pos_size = 64;
785 rdev->config.cayman.sx_max_export_smx_size = 192;
786 rdev->config.cayman.max_hw_contexts = 8;
787 rdev->config.cayman.sq_num_cf_insts = 2;
788
789 rdev->config.cayman.sc_prim_fifo_size = 0x40;
790 rdev->config.cayman.sc_hiz_tile_fifo_size = 0x30;
791 rdev->config.cayman.sc_earlyz_tile_fifo_size = 0x130;
Alex Deucher416a2bd2012-05-31 19:00:25 -0400792 gb_addr_config = ARUBA_GB_ADDR_CONFIG_GOLDEN;
Alex Deucher7b76e472012-03-20 17:18:36 -0400793 break;
Alex Deucherfecf1d02011-03-02 20:07:29 -0500794 }
795
796 /* Initialize HDP */
797 for (i = 0, j = 0; i < 32; i++, j += 0x18) {
798 WREG32((0x2c14 + j), 0x00000000);
799 WREG32((0x2c18 + j), 0x00000000);
800 WREG32((0x2c1c + j), 0x00000000);
801 WREG32((0x2c20 + j), 0x00000000);
802 WREG32((0x2c24 + j), 0x00000000);
803 }
804
805 WREG32(GRBM_CNTL, GRBM_READ_TIMEOUT(0xff));
806
Alex Deucherd054ac12011-09-01 17:46:15 +0000807 evergreen_fix_pci_max_read_req_size(rdev);
808
Alex Deucherfecf1d02011-03-02 20:07:29 -0500809 mc_shared_chmap = RREG32(MC_SHARED_CHMAP);
810 mc_arb_ramcfg = RREG32(MC_ARB_RAMCFG);
811
Alex Deucherfecf1d02011-03-02 20:07:29 -0500812 tmp = (mc_arb_ramcfg & NOOFCOLS_MASK) >> NOOFCOLS_SHIFT;
813 rdev->config.cayman.mem_row_size_in_kb = (4 * (1 << (8 + tmp))) / 1024;
814 if (rdev->config.cayman.mem_row_size_in_kb > 4)
815 rdev->config.cayman.mem_row_size_in_kb = 4;
816 /* XXX use MC settings? */
817 rdev->config.cayman.shader_engine_tile_size = 32;
818 rdev->config.cayman.num_gpus = 1;
819 rdev->config.cayman.multi_gpu_tile_size = 64;
820
Alex Deucherfecf1d02011-03-02 20:07:29 -0500821 tmp = (gb_addr_config & NUM_PIPES_MASK) >> NUM_PIPES_SHIFT;
822 rdev->config.cayman.num_tile_pipes = (1 << tmp);
823 tmp = (gb_addr_config & PIPE_INTERLEAVE_SIZE_MASK) >> PIPE_INTERLEAVE_SIZE_SHIFT;
824 rdev->config.cayman.mem_max_burst_length_bytes = (tmp + 1) * 256;
825 tmp = (gb_addr_config & NUM_SHADER_ENGINES_MASK) >> NUM_SHADER_ENGINES_SHIFT;
826 rdev->config.cayman.num_shader_engines = tmp + 1;
827 tmp = (gb_addr_config & NUM_GPUS_MASK) >> NUM_GPUS_SHIFT;
828 rdev->config.cayman.num_gpus = tmp + 1;
829 tmp = (gb_addr_config & MULTI_GPU_TILE_SIZE_MASK) >> MULTI_GPU_TILE_SIZE_SHIFT;
830 rdev->config.cayman.multi_gpu_tile_size = 1 << tmp;
831 tmp = (gb_addr_config & ROW_SIZE_MASK) >> ROW_SIZE_SHIFT;
832 rdev->config.cayman.mem_row_size_in_kb = 1 << tmp;
833
Alex Deucher416a2bd2012-05-31 19:00:25 -0400834
Alex Deucherfecf1d02011-03-02 20:07:29 -0500835 /* setup tiling info dword. gb_addr_config is not adequate since it does
836 * not have bank info, so create a custom tiling dword.
837 * bits 3:0 num_pipes
838 * bits 7:4 num_banks
839 * bits 11:8 group_size
840 * bits 15:12 row_size
841 */
842 rdev->config.cayman.tile_config = 0;
843 switch (rdev->config.cayman.num_tile_pipes) {
844 case 1:
845 default:
846 rdev->config.cayman.tile_config |= (0 << 0);
847 break;
848 case 2:
849 rdev->config.cayman.tile_config |= (1 << 0);
850 break;
851 case 4:
852 rdev->config.cayman.tile_config |= (2 << 0);
853 break;
854 case 8:
855 rdev->config.cayman.tile_config |= (3 << 0);
856 break;
857 }
Alex Deucher7b76e472012-03-20 17:18:36 -0400858
859 /* num banks is 8 on all fusion asics. 0 = 4, 1 = 8, 2 = 16 */
860 if (rdev->flags & RADEON_IS_IGP)
Alex Deucher1f73cca2012-05-24 22:55:15 -0400861 rdev->config.cayman.tile_config |= 1 << 4;
Alex Deucher29d65402012-05-31 18:53:36 -0400862 else {
Alex Deucher5b23c902012-07-31 11:05:11 -0400863 switch ((mc_arb_ramcfg & NOOFBANK_MASK) >> NOOFBANK_SHIFT) {
864 case 0: /* four banks */
Alex Deucher29d65402012-05-31 18:53:36 -0400865 rdev->config.cayman.tile_config |= 0 << 4;
Alex Deucher5b23c902012-07-31 11:05:11 -0400866 break;
867 case 1: /* eight banks */
868 rdev->config.cayman.tile_config |= 1 << 4;
869 break;
870 case 2: /* sixteen banks */
871 default:
872 rdev->config.cayman.tile_config |= 2 << 4;
873 break;
874 }
Alex Deucher29d65402012-05-31 18:53:36 -0400875 }
Alex Deucherfecf1d02011-03-02 20:07:29 -0500876 rdev->config.cayman.tile_config |=
Dave Airliecde50832011-05-19 14:14:41 +1000877 ((gb_addr_config & PIPE_INTERLEAVE_SIZE_MASK) >> PIPE_INTERLEAVE_SIZE_SHIFT) << 8;
Alex Deucherfecf1d02011-03-02 20:07:29 -0500878 rdev->config.cayman.tile_config |=
879 ((gb_addr_config & ROW_SIZE_MASK) >> ROW_SIZE_SHIFT) << 12;
880
Alex Deucher416a2bd2012-05-31 19:00:25 -0400881 tmp = 0;
882 for (i = (rdev->config.cayman.max_shader_engines - 1); i >= 0; i--) {
883 u32 rb_disable_bitmap;
884
885 WREG32(GRBM_GFX_INDEX, INSTANCE_BROADCAST_WRITES | SE_INDEX(i));
886 WREG32(RLC_GFX_INDEX, INSTANCE_BROADCAST_WRITES | SE_INDEX(i));
887 rb_disable_bitmap = (RREG32(CC_RB_BACKEND_DISABLE) & 0x00ff0000) >> 16;
888 tmp <<= 4;
889 tmp |= rb_disable_bitmap;
890 }
891 /* enabled rb are just the one not disabled :) */
892 disabled_rb_mask = tmp;
Alex Deuchercedb6552013-04-09 10:13:22 -0400893 tmp = 0;
894 for (i = 0; i < (rdev->config.cayman.max_backends_per_se * rdev->config.cayman.max_shader_engines); i++)
895 tmp |= (1 << i);
896 /* if all the backends are disabled, fix it up here */
897 if ((disabled_rb_mask & tmp) == tmp) {
898 for (i = 0; i < (rdev->config.cayman.max_backends_per_se * rdev->config.cayman.max_shader_engines); i++)
899 disabled_rb_mask &= ~(1 << i);
900 }
Alex Deucher416a2bd2012-05-31 19:00:25 -0400901
902 WREG32(GRBM_GFX_INDEX, INSTANCE_BROADCAST_WRITES | SE_BROADCAST_WRITES);
903 WREG32(RLC_GFX_INDEX, INSTANCE_BROADCAST_WRITES | SE_BROADCAST_WRITES);
904
Alex Deucherfecf1d02011-03-02 20:07:29 -0500905 WREG32(GB_ADDR_CONFIG, gb_addr_config);
906 WREG32(DMIF_ADDR_CONFIG, gb_addr_config);
Alex Deucher7c1c7c12013-04-05 10:28:08 -0400907 if (ASIC_IS_DCE6(rdev))
908 WREG32(DMIF_ADDR_CALC, gb_addr_config);
Alex Deucherfecf1d02011-03-02 20:07:29 -0500909 WREG32(HDP_ADDR_CONFIG, gb_addr_config);
Alex Deucherf60cbd12012-12-04 15:27:33 -0500910 WREG32(DMA_TILING_CONFIG + DMA0_REGISTER_OFFSET, gb_addr_config);
911 WREG32(DMA_TILING_CONFIG + DMA1_REGISTER_OFFSET, gb_addr_config);
Christian König9a210592013-04-08 12:41:37 +0200912 WREG32(UVD_UDEC_ADDR_CONFIG, gb_addr_config);
913 WREG32(UVD_UDEC_DB_ADDR_CONFIG, gb_addr_config);
914 WREG32(UVD_UDEC_DBW_ADDR_CONFIG, gb_addr_config);
Alex Deucherfecf1d02011-03-02 20:07:29 -0500915
Alex Deucher8f612b22013-03-11 19:28:39 -0400916 if ((rdev->config.cayman.max_backends_per_se == 1) &&
917 (rdev->flags & RADEON_IS_IGP)) {
918 if ((disabled_rb_mask & 3) == 1) {
919 /* RB0 disabled, RB1 enabled */
920 tmp = 0x11111111;
921 } else {
922 /* RB1 disabled, RB0 enabled */
923 tmp = 0x00000000;
924 }
925 } else {
926 tmp = gb_addr_config & NUM_PIPES_MASK;
927 tmp = r6xx_remap_render_backend(rdev, tmp,
928 rdev->config.cayman.max_backends_per_se *
929 rdev->config.cayman.max_shader_engines,
930 CAYMAN_MAX_BACKENDS, disabled_rb_mask);
931 }
Alex Deucher416a2bd2012-05-31 19:00:25 -0400932 WREG32(GB_BACKEND_MAP, tmp);
Alex Deucherfecf1d02011-03-02 20:07:29 -0500933
Alex Deucher416a2bd2012-05-31 19:00:25 -0400934 cgts_tcc_disable = 0xffff0000;
935 for (i = 0; i < rdev->config.cayman.max_texture_channel_caches; i++)
936 cgts_tcc_disable &= ~(1 << (16 + i));
Alex Deucherfecf1d02011-03-02 20:07:29 -0500937 WREG32(CGTS_TCC_DISABLE, cgts_tcc_disable);
938 WREG32(CGTS_SYS_TCC_DISABLE, cgts_tcc_disable);
Alex Deucherfecf1d02011-03-02 20:07:29 -0500939 WREG32(CGTS_USER_SYS_TCC_DISABLE, cgts_tcc_disable);
940 WREG32(CGTS_USER_TCC_DISABLE, cgts_tcc_disable);
941
942 /* reprogram the shader complex */
943 cgts_sm_ctrl_reg = RREG32(CGTS_SM_CTRL_REG);
944 for (i = 0; i < 16; i++)
945 WREG32(CGTS_SM_CTRL_REG, OVERRIDE);
946 WREG32(CGTS_SM_CTRL_REG, cgts_sm_ctrl_reg);
947
948 /* set HW defaults for 3D engine */
949 WREG32(CP_MEQ_THRESHOLDS, MEQ1_START(0x30) | MEQ2_START(0x60));
950
951 sx_debug_1 = RREG32(SX_DEBUG_1);
952 sx_debug_1 |= ENABLE_NEW_SMX_ADDRESS;
953 WREG32(SX_DEBUG_1, sx_debug_1);
954
955 smx_dc_ctl0 = RREG32(SMX_DC_CTL0);
956 smx_dc_ctl0 &= ~NUMBER_OF_SETS(0x1ff);
Dave Airlie285e0422011-05-09 14:54:33 +1000957 smx_dc_ctl0 |= NUMBER_OF_SETS(rdev->config.cayman.sx_num_of_sets);
Alex Deucherfecf1d02011-03-02 20:07:29 -0500958 WREG32(SMX_DC_CTL0, smx_dc_ctl0);
959
960 WREG32(SPI_CONFIG_CNTL_1, VTX_DONE_DELAY(4) | CRC_SIMD_ID_WADDR_DISABLE);
961
962 /* need to be explicitly zero-ed */
963 WREG32(VGT_OFFCHIP_LDS_BASE, 0);
964 WREG32(SQ_LSTMP_RING_BASE, 0);
965 WREG32(SQ_HSTMP_RING_BASE, 0);
966 WREG32(SQ_ESTMP_RING_BASE, 0);
967 WREG32(SQ_GSTMP_RING_BASE, 0);
968 WREG32(SQ_VSTMP_RING_BASE, 0);
969 WREG32(SQ_PSTMP_RING_BASE, 0);
970
971 WREG32(TA_CNTL_AUX, DISABLE_CUBE_ANISO);
972
Dave Airlie285e0422011-05-09 14:54:33 +1000973 WREG32(SX_EXPORT_BUFFER_SIZES, (COLOR_BUFFER_SIZE((rdev->config.cayman.sx_max_export_size / 4) - 1) |
974 POSITION_BUFFER_SIZE((rdev->config.cayman.sx_max_export_pos_size / 4) - 1) |
975 SMX_BUFFER_SIZE((rdev->config.cayman.sx_max_export_smx_size / 4) - 1)));
Alex Deucherfecf1d02011-03-02 20:07:29 -0500976
Dave Airlie285e0422011-05-09 14:54:33 +1000977 WREG32(PA_SC_FIFO_SIZE, (SC_PRIM_FIFO_SIZE(rdev->config.cayman.sc_prim_fifo_size) |
978 SC_HIZ_TILE_FIFO_SIZE(rdev->config.cayman.sc_hiz_tile_fifo_size) |
979 SC_EARLYZ_TILE_FIFO_SIZE(rdev->config.cayman.sc_earlyz_tile_fifo_size)));
Alex Deucherfecf1d02011-03-02 20:07:29 -0500980
981
982 WREG32(VGT_NUM_INSTANCES, 1);
983
984 WREG32(CP_PERFMON_CNTL, 0);
985
Dave Airlie285e0422011-05-09 14:54:33 +1000986 WREG32(SQ_MS_FIFO_SIZES, (CACHE_FIFO_SIZE(16 * rdev->config.cayman.sq_num_cf_insts) |
Alex Deucherfecf1d02011-03-02 20:07:29 -0500987 FETCH_FIFO_HIWATER(0x4) |
988 DONE_FIFO_HIWATER(0xe0) |
989 ALU_UPDATE_FIFO_HIWATER(0x8)));
990
991 WREG32(SQ_GPR_RESOURCE_MGMT_1, NUM_CLAUSE_TEMP_GPRS(4));
992 WREG32(SQ_CONFIG, (VC_ENABLE |
993 EXPORT_SRC_C |
994 GFX_PRIO(0) |
995 CS1_PRIO(0) |
996 CS2_PRIO(1)));
997 WREG32(SQ_DYN_GPR_CNTL_PS_FLUSH_REQ, DYN_GPR_ENABLE);
998
999 WREG32(PA_SC_FORCE_EOV_MAX_CNTS, (FORCE_EOV_MAX_CLK_CNT(4095) |
1000 FORCE_EOV_MAX_REZ_CNT(255)));
1001
1002 WREG32(VGT_CACHE_INVALIDATION, CACHE_INVALIDATION(VC_AND_TC) |
1003 AUTO_INVLD_EN(ES_AND_GS_AUTO));
1004
1005 WREG32(VGT_GS_VERTEX_REUSE, 16);
1006 WREG32(PA_SC_LINE_STIPPLE_STATE, 0);
1007
1008 WREG32(CB_PERF_CTR0_SEL_0, 0);
1009 WREG32(CB_PERF_CTR0_SEL_1, 0);
1010 WREG32(CB_PERF_CTR1_SEL_0, 0);
1011 WREG32(CB_PERF_CTR1_SEL_1, 0);
1012 WREG32(CB_PERF_CTR2_SEL_0, 0);
1013 WREG32(CB_PERF_CTR2_SEL_1, 0);
1014 WREG32(CB_PERF_CTR3_SEL_0, 0);
1015 WREG32(CB_PERF_CTR3_SEL_1, 0);
1016
Dave Airlie0b65f832011-05-19 14:14:42 +10001017 tmp = RREG32(HDP_MISC_CNTL);
1018 tmp |= HDP_FLUSH_INVALIDATE_CACHE;
1019 WREG32(HDP_MISC_CNTL, tmp);
1020
Alex Deucherfecf1d02011-03-02 20:07:29 -05001021 hdp_host_path_cntl = RREG32(HDP_HOST_PATH_CNTL);
1022 WREG32(HDP_HOST_PATH_CNTL, hdp_host_path_cntl);
1023
1024 WREG32(PA_CL_ENHANCE, CLIP_VTX_REORDER_ENA | NUM_CLIP_SEQ(3));
1025
1026 udelay(50);
1027}
1028
Alex Deucherfa8198e2011-03-02 20:07:30 -05001029/*
1030 * GART
1031 */
1032void cayman_pcie_gart_tlb_flush(struct radeon_device *rdev)
1033{
1034 /* flush hdp cache */
1035 WREG32(HDP_MEM_COHERENCY_FLUSH_CNTL, 0x1);
1036
1037 /* bits 0-7 are the VM contexts0-7 */
1038 WREG32(VM_INVALIDATE_REQUEST, 1);
1039}
1040
Lauri Kasanen1109ca02012-08-31 13:43:50 -04001041static int cayman_pcie_gart_enable(struct radeon_device *rdev)
Alex Deucherfa8198e2011-03-02 20:07:30 -05001042{
Jerome Glisse721604a2012-01-05 22:11:05 -05001043 int i, r;
Alex Deucherfa8198e2011-03-02 20:07:30 -05001044
Jerome Glissec9a1be92011-11-03 11:16:49 -04001045 if (rdev->gart.robj == NULL) {
Alex Deucherfa8198e2011-03-02 20:07:30 -05001046 dev_err(rdev->dev, "No VRAM object for PCIE GART.\n");
1047 return -EINVAL;
1048 }
1049 r = radeon_gart_table_vram_pin(rdev);
1050 if (r)
1051 return r;
1052 radeon_gart_restore(rdev);
1053 /* Setup TLB control */
Jerome Glisse721604a2012-01-05 22:11:05 -05001054 WREG32(MC_VM_MX_L1_TLB_CNTL,
1055 (0xA << 7) |
1056 ENABLE_L1_TLB |
Alex Deucherfa8198e2011-03-02 20:07:30 -05001057 ENABLE_L1_FRAGMENT_PROCESSING |
1058 SYSTEM_ACCESS_MODE_NOT_IN_SYS |
Jerome Glisse721604a2012-01-05 22:11:05 -05001059 ENABLE_ADVANCED_DRIVER_MODEL |
Alex Deucherfa8198e2011-03-02 20:07:30 -05001060 SYSTEM_APERTURE_UNMAPPED_ACCESS_PASS_THRU);
1061 /* Setup L2 cache */
1062 WREG32(VM_L2_CNTL, ENABLE_L2_CACHE |
1063 ENABLE_L2_PTE_CACHE_LRU_UPDATE_BY_WRITE |
1064 ENABLE_L2_PDE0_CACHE_LRU_UPDATE_BY_WRITE |
1065 EFFECTIVE_L2_QUEUE_SIZE(7) |
1066 CONTEXT1_IDENTITY_ACCESS_MODE(1));
1067 WREG32(VM_L2_CNTL2, INVALIDATE_ALL_L1_TLBS | INVALIDATE_L2_CACHE);
1068 WREG32(VM_L2_CNTL3, L2_CACHE_BIGK_ASSOCIATIVITY |
1069 L2_CACHE_BIGK_FRAGMENT_SIZE(6));
1070 /* setup context0 */
1071 WREG32(VM_CONTEXT0_PAGE_TABLE_START_ADDR, rdev->mc.gtt_start >> 12);
1072 WREG32(VM_CONTEXT0_PAGE_TABLE_END_ADDR, rdev->mc.gtt_end >> 12);
1073 WREG32(VM_CONTEXT0_PAGE_TABLE_BASE_ADDR, rdev->gart.table_addr >> 12);
1074 WREG32(VM_CONTEXT0_PROTECTION_FAULT_DEFAULT_ADDR,
1075 (u32)(rdev->dummy_page.addr >> 12));
1076 WREG32(VM_CONTEXT0_CNTL2, 0);
1077 WREG32(VM_CONTEXT0_CNTL, ENABLE_CONTEXT | PAGE_TABLE_DEPTH(0) |
1078 RANGE_PROTECTION_FAULT_ENABLE_DEFAULT);
Jerome Glisse721604a2012-01-05 22:11:05 -05001079
1080 WREG32(0x15D4, 0);
1081 WREG32(0x15D8, 0);
1082 WREG32(0x15DC, 0);
1083
1084 /* empty context1-7 */
Alex Deucher23d4f1f2012-10-08 09:45:46 -04001085 /* Assign the pt base to something valid for now; the pts used for
1086 * the VMs are determined by the application and setup and assigned
1087 * on the fly in the vm part of radeon_gart.c
1088 */
Jerome Glisse721604a2012-01-05 22:11:05 -05001089 for (i = 1; i < 8; i++) {
1090 WREG32(VM_CONTEXT0_PAGE_TABLE_START_ADDR + (i << 2), 0);
Alex Deucherc1a7ca02012-10-08 12:15:13 -04001091 WREG32(VM_CONTEXT0_PAGE_TABLE_END_ADDR + (i << 2), rdev->vm_manager.max_pfn);
Jerome Glisse721604a2012-01-05 22:11:05 -05001092 WREG32(VM_CONTEXT0_PAGE_TABLE_BASE_ADDR + (i << 2),
1093 rdev->gart.table_addr >> 12);
1094 }
1095
1096 /* enable context1-7 */
1097 WREG32(VM_CONTEXT1_PROTECTION_FAULT_DEFAULT_ADDR,
1098 (u32)(rdev->dummy_page.addr >> 12));
Christian Königae133a12012-09-18 15:30:44 -04001099 WREG32(VM_CONTEXT1_CNTL2, 4);
Dmitry Cherkasovfa87e622012-09-17 19:36:19 +02001100 WREG32(VM_CONTEXT1_CNTL, ENABLE_CONTEXT | PAGE_TABLE_DEPTH(1) |
Christian Königae133a12012-09-18 15:30:44 -04001101 RANGE_PROTECTION_FAULT_ENABLE_INTERRUPT |
1102 RANGE_PROTECTION_FAULT_ENABLE_DEFAULT |
1103 DUMMY_PAGE_PROTECTION_FAULT_ENABLE_INTERRUPT |
1104 DUMMY_PAGE_PROTECTION_FAULT_ENABLE_DEFAULT |
1105 PDE0_PROTECTION_FAULT_ENABLE_INTERRUPT |
1106 PDE0_PROTECTION_FAULT_ENABLE_DEFAULT |
1107 VALID_PROTECTION_FAULT_ENABLE_INTERRUPT |
1108 VALID_PROTECTION_FAULT_ENABLE_DEFAULT |
1109 READ_PROTECTION_FAULT_ENABLE_INTERRUPT |
1110 READ_PROTECTION_FAULT_ENABLE_DEFAULT |
1111 WRITE_PROTECTION_FAULT_ENABLE_INTERRUPT |
1112 WRITE_PROTECTION_FAULT_ENABLE_DEFAULT);
Alex Deucherfa8198e2011-03-02 20:07:30 -05001113
1114 cayman_pcie_gart_tlb_flush(rdev);
Tormod Voldenfcf4de52011-08-31 21:54:07 +00001115 DRM_INFO("PCIE GART of %uM enabled (table at 0x%016llX).\n",
1116 (unsigned)(rdev->mc.gtt_size >> 20),
1117 (unsigned long long)rdev->gart.table_addr);
Alex Deucherfa8198e2011-03-02 20:07:30 -05001118 rdev->gart.ready = true;
1119 return 0;
1120}
1121
Lauri Kasanen1109ca02012-08-31 13:43:50 -04001122static void cayman_pcie_gart_disable(struct radeon_device *rdev)
Alex Deucherfa8198e2011-03-02 20:07:30 -05001123{
Alex Deucherfa8198e2011-03-02 20:07:30 -05001124 /* Disable all tables */
1125 WREG32(VM_CONTEXT0_CNTL, 0);
1126 WREG32(VM_CONTEXT1_CNTL, 0);
1127 /* Setup TLB control */
1128 WREG32(MC_VM_MX_L1_TLB_CNTL, ENABLE_L1_FRAGMENT_PROCESSING |
1129 SYSTEM_ACCESS_MODE_NOT_IN_SYS |
1130 SYSTEM_APERTURE_UNMAPPED_ACCESS_PASS_THRU);
1131 /* Setup L2 cache */
1132 WREG32(VM_L2_CNTL, ENABLE_L2_PTE_CACHE_LRU_UPDATE_BY_WRITE |
1133 ENABLE_L2_PDE0_CACHE_LRU_UPDATE_BY_WRITE |
1134 EFFECTIVE_L2_QUEUE_SIZE(7) |
1135 CONTEXT1_IDENTITY_ACCESS_MODE(1));
1136 WREG32(VM_L2_CNTL2, 0);
1137 WREG32(VM_L2_CNTL3, L2_CACHE_BIGK_ASSOCIATIVITY |
1138 L2_CACHE_BIGK_FRAGMENT_SIZE(6));
Jerome Glissec9a1be92011-11-03 11:16:49 -04001139 radeon_gart_table_vram_unpin(rdev);
Alex Deucherfa8198e2011-03-02 20:07:30 -05001140}
1141
Lauri Kasanen1109ca02012-08-31 13:43:50 -04001142static void cayman_pcie_gart_fini(struct radeon_device *rdev)
Alex Deucherfa8198e2011-03-02 20:07:30 -05001143{
1144 cayman_pcie_gart_disable(rdev);
1145 radeon_gart_table_vram_free(rdev);
1146 radeon_gart_fini(rdev);
1147}
1148
Alex Deucher1b370782011-11-17 20:13:28 -05001149void cayman_cp_int_cntl_setup(struct radeon_device *rdev,
1150 int ring, u32 cp_int_cntl)
1151{
1152 u32 srbm_gfx_cntl = RREG32(SRBM_GFX_CNTL) & ~3;
1153
1154 WREG32(SRBM_GFX_CNTL, srbm_gfx_cntl | (ring & 3));
1155 WREG32(CP_INT_CNTL, cp_int_cntl);
1156}
1157
Alex Deucher0c88a022011-03-02 20:07:31 -05001158/*
1159 * CP.
1160 */
Alex Deucherb40e7e12011-11-17 14:57:50 -05001161void cayman_fence_ring_emit(struct radeon_device *rdev,
1162 struct radeon_fence *fence)
1163{
1164 struct radeon_ring *ring = &rdev->ring[fence->ring];
1165 u64 addr = rdev->fence_drv[fence->ring].gpu_addr;
1166
Jerome Glisse721604a2012-01-05 22:11:05 -05001167 /* flush read cache over gart for this vmid */
1168 radeon_ring_write(ring, PACKET3(PACKET3_SET_CONFIG_REG, 1));
1169 radeon_ring_write(ring, (CP_COHER_CNTL2 - PACKET3_SET_CONFIG_REG_START) >> 2);
1170 radeon_ring_write(ring, 0);
Alex Deucherb40e7e12011-11-17 14:57:50 -05001171 radeon_ring_write(ring, PACKET3(PACKET3_SURFACE_SYNC, 3));
1172 radeon_ring_write(ring, PACKET3_TC_ACTION_ENA | PACKET3_SH_ACTION_ENA);
1173 radeon_ring_write(ring, 0xFFFFFFFF);
1174 radeon_ring_write(ring, 0);
1175 radeon_ring_write(ring, 10); /* poll interval */
1176 /* EVENT_WRITE_EOP - flush caches, send int */
1177 radeon_ring_write(ring, PACKET3(PACKET3_EVENT_WRITE_EOP, 4));
1178 radeon_ring_write(ring, EVENT_TYPE(CACHE_FLUSH_AND_INV_EVENT_TS) | EVENT_INDEX(5));
1179 radeon_ring_write(ring, addr & 0xffffffff);
1180 radeon_ring_write(ring, (upper_32_bits(addr) & 0xff) | DATA_SEL(1) | INT_SEL(2));
1181 radeon_ring_write(ring, fence->seq);
1182 radeon_ring_write(ring, 0);
1183}
1184
Jerome Glisse721604a2012-01-05 22:11:05 -05001185void cayman_ring_ib_execute(struct radeon_device *rdev, struct radeon_ib *ib)
1186{
Christian König876dc9f2012-05-08 14:24:01 +02001187 struct radeon_ring *ring = &rdev->ring[ib->ring];
Jerome Glisse721604a2012-01-05 22:11:05 -05001188
1189 /* set to DX10/11 mode */
1190 radeon_ring_write(ring, PACKET3(PACKET3_MODE_CONTROL, 0));
1191 radeon_ring_write(ring, 1);
Christian König45df6802012-07-06 16:22:55 +02001192
1193 if (ring->rptr_save_reg) {
1194 uint32_t next_rptr = ring->wptr + 3 + 4 + 8;
1195 radeon_ring_write(ring, PACKET3(PACKET3_SET_CONFIG_REG, 1));
1196 radeon_ring_write(ring, ((ring->rptr_save_reg -
1197 PACKET3_SET_CONFIG_REG_START) >> 2));
1198 radeon_ring_write(ring, next_rptr);
1199 }
1200
Jerome Glisse721604a2012-01-05 22:11:05 -05001201 radeon_ring_write(ring, PACKET3(PACKET3_INDIRECT_BUFFER, 2));
1202 radeon_ring_write(ring,
1203#ifdef __BIG_ENDIAN
1204 (2 << 0) |
1205#endif
1206 (ib->gpu_addr & 0xFFFFFFFC));
1207 radeon_ring_write(ring, upper_32_bits(ib->gpu_addr) & 0xFF);
Christian König4bf3dd92012-08-06 18:57:44 +02001208 radeon_ring_write(ring, ib->length_dw |
1209 (ib->vm ? (ib->vm->id << 24) : 0));
Jerome Glisse721604a2012-01-05 22:11:05 -05001210
1211 /* flush read cache over gart for this vmid */
1212 radeon_ring_write(ring, PACKET3(PACKET3_SET_CONFIG_REG, 1));
1213 radeon_ring_write(ring, (CP_COHER_CNTL2 - PACKET3_SET_CONFIG_REG_START) >> 2);
Christian König4bf3dd92012-08-06 18:57:44 +02001214 radeon_ring_write(ring, ib->vm ? ib->vm->id : 0);
Jerome Glisse721604a2012-01-05 22:11:05 -05001215 radeon_ring_write(ring, PACKET3(PACKET3_SURFACE_SYNC, 3));
1216 radeon_ring_write(ring, PACKET3_TC_ACTION_ENA | PACKET3_SH_ACTION_ENA);
1217 radeon_ring_write(ring, 0xFFFFFFFF);
1218 radeon_ring_write(ring, 0);
1219 radeon_ring_write(ring, 10); /* poll interval */
1220}
1221
Christian Königf2ba57b2013-04-08 12:41:29 +02001222void cayman_uvd_semaphore_emit(struct radeon_device *rdev,
1223 struct radeon_ring *ring,
1224 struct radeon_semaphore *semaphore,
1225 bool emit_wait)
1226{
1227 uint64_t addr = semaphore->gpu_addr;
1228
1229 radeon_ring_write(ring, PACKET0(UVD_SEMA_ADDR_LOW, 0));
1230 radeon_ring_write(ring, (addr >> 3) & 0x000FFFFF);
1231
1232 radeon_ring_write(ring, PACKET0(UVD_SEMA_ADDR_HIGH, 0));
1233 radeon_ring_write(ring, (addr >> 23) & 0x000FFFFF);
1234
1235 radeon_ring_write(ring, PACKET0(UVD_SEMA_CMD, 0));
1236 radeon_ring_write(ring, 0x80 | (emit_wait ? 1 : 0));
1237}
1238
Alex Deucher0c88a022011-03-02 20:07:31 -05001239static void cayman_cp_enable(struct radeon_device *rdev, bool enable)
1240{
1241 if (enable)
1242 WREG32(CP_ME_CNTL, 0);
1243 else {
Dave Airlie38f1cff2011-03-16 11:34:41 +10001244 radeon_ttm_set_active_vram_size(rdev, rdev->mc.visible_vram_size);
Alex Deucher0c88a022011-03-02 20:07:31 -05001245 WREG32(CP_ME_CNTL, (CP_ME_HALT | CP_PFP_HALT));
1246 WREG32(SCRATCH_UMSK, 0);
Alex Deucherf60cbd12012-12-04 15:27:33 -05001247 rdev->ring[RADEON_RING_TYPE_GFX_INDEX].ready = false;
Alex Deucher0c88a022011-03-02 20:07:31 -05001248 }
1249}
1250
1251static int cayman_cp_load_microcode(struct radeon_device *rdev)
1252{
1253 const __be32 *fw_data;
1254 int i;
1255
1256 if (!rdev->me_fw || !rdev->pfp_fw)
1257 return -EINVAL;
1258
1259 cayman_cp_enable(rdev, false);
1260
1261 fw_data = (const __be32 *)rdev->pfp_fw->data;
1262 WREG32(CP_PFP_UCODE_ADDR, 0);
1263 for (i = 0; i < CAYMAN_PFP_UCODE_SIZE; i++)
1264 WREG32(CP_PFP_UCODE_DATA, be32_to_cpup(fw_data++));
1265 WREG32(CP_PFP_UCODE_ADDR, 0);
1266
1267 fw_data = (const __be32 *)rdev->me_fw->data;
1268 WREG32(CP_ME_RAM_WADDR, 0);
1269 for (i = 0; i < CAYMAN_PM4_UCODE_SIZE; i++)
1270 WREG32(CP_ME_RAM_DATA, be32_to_cpup(fw_data++));
1271
1272 WREG32(CP_PFP_UCODE_ADDR, 0);
1273 WREG32(CP_ME_RAM_WADDR, 0);
1274 WREG32(CP_ME_RAM_RADDR, 0);
1275 return 0;
1276}
1277
1278static int cayman_cp_start(struct radeon_device *rdev)
1279{
Christian Könige32eb502011-10-23 12:56:27 +02001280 struct radeon_ring *ring = &rdev->ring[RADEON_RING_TYPE_GFX_INDEX];
Alex Deucher0c88a022011-03-02 20:07:31 -05001281 int r, i;
1282
Christian Könige32eb502011-10-23 12:56:27 +02001283 r = radeon_ring_lock(rdev, ring, 7);
Alex Deucher0c88a022011-03-02 20:07:31 -05001284 if (r) {
1285 DRM_ERROR("radeon: cp failed to lock ring (%d).\n", r);
1286 return r;
1287 }
Christian Könige32eb502011-10-23 12:56:27 +02001288 radeon_ring_write(ring, PACKET3(PACKET3_ME_INITIALIZE, 5));
1289 radeon_ring_write(ring, 0x1);
1290 radeon_ring_write(ring, 0x0);
1291 radeon_ring_write(ring, rdev->config.cayman.max_hw_contexts - 1);
1292 radeon_ring_write(ring, PACKET3_ME_INITIALIZE_DEVICE_ID(1));
1293 radeon_ring_write(ring, 0);
1294 radeon_ring_write(ring, 0);
1295 radeon_ring_unlock_commit(rdev, ring);
Alex Deucher0c88a022011-03-02 20:07:31 -05001296
1297 cayman_cp_enable(rdev, true);
1298
Christian Könige32eb502011-10-23 12:56:27 +02001299 r = radeon_ring_lock(rdev, ring, cayman_default_size + 19);
Alex Deucher0c88a022011-03-02 20:07:31 -05001300 if (r) {
1301 DRM_ERROR("radeon: cp failed to lock ring (%d).\n", r);
1302 return r;
1303 }
1304
1305 /* setup clear context state */
Christian Könige32eb502011-10-23 12:56:27 +02001306 radeon_ring_write(ring, PACKET3(PACKET3_PREAMBLE_CNTL, 0));
1307 radeon_ring_write(ring, PACKET3_PREAMBLE_BEGIN_CLEAR_STATE);
Alex Deucher0c88a022011-03-02 20:07:31 -05001308
1309 for (i = 0; i < cayman_default_size; i++)
Christian Könige32eb502011-10-23 12:56:27 +02001310 radeon_ring_write(ring, cayman_default_state[i]);
Alex Deucher0c88a022011-03-02 20:07:31 -05001311
Christian Könige32eb502011-10-23 12:56:27 +02001312 radeon_ring_write(ring, PACKET3(PACKET3_PREAMBLE_CNTL, 0));
1313 radeon_ring_write(ring, PACKET3_PREAMBLE_END_CLEAR_STATE);
Alex Deucher0c88a022011-03-02 20:07:31 -05001314
1315 /* set clear context state */
Christian Könige32eb502011-10-23 12:56:27 +02001316 radeon_ring_write(ring, PACKET3(PACKET3_CLEAR_STATE, 0));
1317 radeon_ring_write(ring, 0);
Alex Deucher0c88a022011-03-02 20:07:31 -05001318
1319 /* SQ_VTX_BASE_VTX_LOC */
Christian Könige32eb502011-10-23 12:56:27 +02001320 radeon_ring_write(ring, 0xc0026f00);
1321 radeon_ring_write(ring, 0x00000000);
1322 radeon_ring_write(ring, 0x00000000);
1323 radeon_ring_write(ring, 0x00000000);
Alex Deucher0c88a022011-03-02 20:07:31 -05001324
1325 /* Clear consts */
Christian Könige32eb502011-10-23 12:56:27 +02001326 radeon_ring_write(ring, 0xc0036f00);
1327 radeon_ring_write(ring, 0x00000bc4);
1328 radeon_ring_write(ring, 0xffffffff);
1329 radeon_ring_write(ring, 0xffffffff);
1330 radeon_ring_write(ring, 0xffffffff);
Alex Deucher0c88a022011-03-02 20:07:31 -05001331
Christian Könige32eb502011-10-23 12:56:27 +02001332 radeon_ring_write(ring, 0xc0026900);
1333 radeon_ring_write(ring, 0x00000316);
1334 radeon_ring_write(ring, 0x0000000e); /* VGT_VERTEX_REUSE_BLOCK_CNTL */
1335 radeon_ring_write(ring, 0x00000010); /* */
Alex Deucher9b91d182011-03-02 20:07:39 -05001336
Christian Könige32eb502011-10-23 12:56:27 +02001337 radeon_ring_unlock_commit(rdev, ring);
Alex Deucher0c88a022011-03-02 20:07:31 -05001338
1339 /* XXX init other rings */
1340
1341 return 0;
1342}
1343
Alex Deucher755d8192011-03-02 20:07:34 -05001344static void cayman_cp_fini(struct radeon_device *rdev)
1345{
Christian König45df6802012-07-06 16:22:55 +02001346 struct radeon_ring *ring = &rdev->ring[RADEON_RING_TYPE_GFX_INDEX];
Alex Deucher755d8192011-03-02 20:07:34 -05001347 cayman_cp_enable(rdev, false);
Christian König45df6802012-07-06 16:22:55 +02001348 radeon_ring_fini(rdev, ring);
1349 radeon_scratch_free(rdev, ring->rptr_save_reg);
Alex Deucher755d8192011-03-02 20:07:34 -05001350}
1351
Lauri Kasanen1109ca02012-08-31 13:43:50 -04001352static int cayman_cp_resume(struct radeon_device *rdev)
Alex Deucher0c88a022011-03-02 20:07:31 -05001353{
Christian Königb90ca982012-07-04 21:36:53 +02001354 static const int ridx[] = {
1355 RADEON_RING_TYPE_GFX_INDEX,
1356 CAYMAN_RING_TYPE_CP1_INDEX,
1357 CAYMAN_RING_TYPE_CP2_INDEX
1358 };
1359 static const unsigned cp_rb_cntl[] = {
1360 CP_RB0_CNTL,
1361 CP_RB1_CNTL,
1362 CP_RB2_CNTL,
1363 };
1364 static const unsigned cp_rb_rptr_addr[] = {
1365 CP_RB0_RPTR_ADDR,
1366 CP_RB1_RPTR_ADDR,
1367 CP_RB2_RPTR_ADDR
1368 };
1369 static const unsigned cp_rb_rptr_addr_hi[] = {
1370 CP_RB0_RPTR_ADDR_HI,
1371 CP_RB1_RPTR_ADDR_HI,
1372 CP_RB2_RPTR_ADDR_HI
1373 };
1374 static const unsigned cp_rb_base[] = {
1375 CP_RB0_BASE,
1376 CP_RB1_BASE,
1377 CP_RB2_BASE
1378 };
Christian Könige32eb502011-10-23 12:56:27 +02001379 struct radeon_ring *ring;
Christian Königb90ca982012-07-04 21:36:53 +02001380 int i, r;
Alex Deucher0c88a022011-03-02 20:07:31 -05001381
1382 /* Reset cp; if cp is reset, then PA, SH, VGT also need to be reset */
1383 WREG32(GRBM_SOFT_RESET, (SOFT_RESET_CP |
1384 SOFT_RESET_PA |
1385 SOFT_RESET_SH |
1386 SOFT_RESET_VGT |
Jerome Glissea49a50d2011-08-24 20:00:17 +00001387 SOFT_RESET_SPI |
Alex Deucher0c88a022011-03-02 20:07:31 -05001388 SOFT_RESET_SX));
1389 RREG32(GRBM_SOFT_RESET);
1390 mdelay(15);
1391 WREG32(GRBM_SOFT_RESET, 0);
1392 RREG32(GRBM_SOFT_RESET);
1393
Christian König15d33322011-09-15 19:02:22 +02001394 WREG32(CP_SEM_WAIT_TIMER, 0x0);
Alex Deucher11ef3f12012-01-20 14:47:43 -05001395 WREG32(CP_SEM_INCOMPLETE_TIMER_CNTL, 0x0);
Alex Deucher0c88a022011-03-02 20:07:31 -05001396
1397 /* Set the write pointer delay */
1398 WREG32(CP_RB_WPTR_DELAY, 0);
1399
1400 WREG32(CP_DEBUG, (1 << 27));
1401
Adam Buchbinder48fc7f72012-09-19 21:48:00 -04001402 /* set the wb address whether it's enabled or not */
Alex Deucher0c88a022011-03-02 20:07:31 -05001403 WREG32(SCRATCH_ADDR, ((rdev->wb.gpu_addr + RADEON_WB_SCRATCH_OFFSET) >> 8) & 0xFFFFFFFF);
Christian Königb90ca982012-07-04 21:36:53 +02001404 WREG32(SCRATCH_UMSK, 0xff);
Alex Deucher0c88a022011-03-02 20:07:31 -05001405
Christian Königb90ca982012-07-04 21:36:53 +02001406 for (i = 0; i < 3; ++i) {
1407 uint32_t rb_cntl;
1408 uint64_t addr;
1409
1410 /* Set ring buffer size */
1411 ring = &rdev->ring[ridx[i]];
1412 rb_cntl = drm_order(ring->ring_size / 8);
1413 rb_cntl |= drm_order(RADEON_GPU_PAGE_SIZE/8) << 8;
1414#ifdef __BIG_ENDIAN
1415 rb_cntl |= BUF_SWAP_32BIT;
1416#endif
1417 WREG32(cp_rb_cntl[i], rb_cntl);
1418
Adam Buchbinder48fc7f72012-09-19 21:48:00 -04001419 /* set the wb address whether it's enabled or not */
Christian Königb90ca982012-07-04 21:36:53 +02001420 addr = rdev->wb.gpu_addr + RADEON_WB_CP_RPTR_OFFSET;
1421 WREG32(cp_rb_rptr_addr[i], addr & 0xFFFFFFFC);
1422 WREG32(cp_rb_rptr_addr_hi[i], upper_32_bits(addr) & 0xFF);
Alex Deucher0c88a022011-03-02 20:07:31 -05001423 }
1424
Christian Königb90ca982012-07-04 21:36:53 +02001425 /* set the rb base addr, this causes an internal reset of ALL rings */
1426 for (i = 0; i < 3; ++i) {
1427 ring = &rdev->ring[ridx[i]];
1428 WREG32(cp_rb_base[i], ring->gpu_addr >> 8);
1429 }
Alex Deucher0c88a022011-03-02 20:07:31 -05001430
Christian Königb90ca982012-07-04 21:36:53 +02001431 for (i = 0; i < 3; ++i) {
1432 /* Initialize the ring buffer's read and write pointers */
1433 ring = &rdev->ring[ridx[i]];
1434 WREG32_P(cp_rb_cntl[i], RB_RPTR_WR_ENA, ~RB_RPTR_WR_ENA);
Alex Deucher0c88a022011-03-02 20:07:31 -05001435
Christian Königb90ca982012-07-04 21:36:53 +02001436 ring->rptr = ring->wptr = 0;
1437 WREG32(ring->rptr_reg, ring->rptr);
1438 WREG32(ring->wptr_reg, ring->wptr);
Alex Deucher0c88a022011-03-02 20:07:31 -05001439
Christian Königb90ca982012-07-04 21:36:53 +02001440 mdelay(1);
1441 WREG32_P(cp_rb_cntl[i], 0, ~RB_RPTR_WR_ENA);
1442 }
Alex Deucher0c88a022011-03-02 20:07:31 -05001443
1444 /* start the rings */
1445 cayman_cp_start(rdev);
Christian Könige32eb502011-10-23 12:56:27 +02001446 rdev->ring[RADEON_RING_TYPE_GFX_INDEX].ready = true;
1447 rdev->ring[CAYMAN_RING_TYPE_CP1_INDEX].ready = false;
1448 rdev->ring[CAYMAN_RING_TYPE_CP2_INDEX].ready = false;
Alex Deucher0c88a022011-03-02 20:07:31 -05001449 /* this only test cp0 */
Alex Deucherf7128122012-02-23 17:53:45 -05001450 r = radeon_ring_test(rdev, RADEON_RING_TYPE_GFX_INDEX, &rdev->ring[RADEON_RING_TYPE_GFX_INDEX]);
Alex Deucher0c88a022011-03-02 20:07:31 -05001451 if (r) {
Christian Könige32eb502011-10-23 12:56:27 +02001452 rdev->ring[RADEON_RING_TYPE_GFX_INDEX].ready = false;
1453 rdev->ring[CAYMAN_RING_TYPE_CP1_INDEX].ready = false;
1454 rdev->ring[CAYMAN_RING_TYPE_CP2_INDEX].ready = false;
Alex Deucher0c88a022011-03-02 20:07:31 -05001455 return r;
1456 }
1457
1458 return 0;
1459}
1460
Alex Deucherf60cbd12012-12-04 15:27:33 -05001461/*
1462 * DMA
1463 * Starting with R600, the GPU has an asynchronous
1464 * DMA engine. The programming model is very similar
1465 * to the 3D engine (ring buffer, IBs, etc.), but the
1466 * DMA controller has it's own packet format that is
1467 * different form the PM4 format used by the 3D engine.
1468 * It supports copying data, writing embedded data,
1469 * solid fills, and a number of other things. It also
1470 * has support for tiling/detiling of buffers.
1471 * Cayman and newer support two asynchronous DMA engines.
1472 */
1473/**
1474 * cayman_dma_ring_ib_execute - Schedule an IB on the DMA engine
1475 *
1476 * @rdev: radeon_device pointer
1477 * @ib: IB object to schedule
1478 *
1479 * Schedule an IB in the DMA ring (cayman-SI).
1480 */
1481void cayman_dma_ring_ib_execute(struct radeon_device *rdev,
1482 struct radeon_ib *ib)
1483{
1484 struct radeon_ring *ring = &rdev->ring[ib->ring];
1485
1486 if (rdev->wb.enabled) {
1487 u32 next_rptr = ring->wptr + 4;
1488 while ((next_rptr & 7) != 5)
1489 next_rptr++;
1490 next_rptr += 3;
1491 radeon_ring_write(ring, DMA_PACKET(DMA_PACKET_WRITE, 0, 0, 1));
1492 radeon_ring_write(ring, ring->next_rptr_gpu_addr & 0xfffffffc);
1493 radeon_ring_write(ring, upper_32_bits(ring->next_rptr_gpu_addr) & 0xff);
1494 radeon_ring_write(ring, next_rptr);
1495 }
1496
1497 /* The indirect buffer packet must end on an 8 DW boundary in the DMA ring.
1498 * Pad as necessary with NOPs.
1499 */
1500 while ((ring->wptr & 7) != 5)
1501 radeon_ring_write(ring, DMA_PACKET(DMA_PACKET_NOP, 0, 0, 0));
1502 radeon_ring_write(ring, DMA_IB_PACKET(DMA_PACKET_INDIRECT_BUFFER, ib->vm ? ib->vm->id : 0, 0));
1503 radeon_ring_write(ring, (ib->gpu_addr & 0xFFFFFFE0));
1504 radeon_ring_write(ring, (ib->length_dw << 12) | (upper_32_bits(ib->gpu_addr) & 0xFF));
1505
1506}
1507
1508/**
1509 * cayman_dma_stop - stop the async dma engines
1510 *
1511 * @rdev: radeon_device pointer
1512 *
1513 * Stop the async dma engines (cayman-SI).
1514 */
1515void cayman_dma_stop(struct radeon_device *rdev)
1516{
1517 u32 rb_cntl;
1518
1519 radeon_ttm_set_active_vram_size(rdev, rdev->mc.visible_vram_size);
1520
1521 /* dma0 */
1522 rb_cntl = RREG32(DMA_RB_CNTL + DMA0_REGISTER_OFFSET);
1523 rb_cntl &= ~DMA_RB_ENABLE;
1524 WREG32(DMA_RB_CNTL + DMA0_REGISTER_OFFSET, rb_cntl);
1525
1526 /* dma1 */
1527 rb_cntl = RREG32(DMA_RB_CNTL + DMA1_REGISTER_OFFSET);
1528 rb_cntl &= ~DMA_RB_ENABLE;
1529 WREG32(DMA_RB_CNTL + DMA1_REGISTER_OFFSET, rb_cntl);
1530
1531 rdev->ring[R600_RING_TYPE_DMA_INDEX].ready = false;
1532 rdev->ring[CAYMAN_RING_TYPE_DMA1_INDEX].ready = false;
1533}
1534
1535/**
1536 * cayman_dma_resume - setup and start the async dma engines
1537 *
1538 * @rdev: radeon_device pointer
1539 *
1540 * Set up the DMA ring buffers and enable them. (cayman-SI).
1541 * Returns 0 for success, error for failure.
1542 */
1543int cayman_dma_resume(struct radeon_device *rdev)
1544{
1545 struct radeon_ring *ring;
Michel Dänzerb3dfcb22013-01-24 19:02:01 +01001546 u32 rb_cntl, dma_cntl, ib_cntl;
Alex Deucherf60cbd12012-12-04 15:27:33 -05001547 u32 rb_bufsz;
1548 u32 reg_offset, wb_offset;
1549 int i, r;
1550
1551 /* Reset dma */
1552 WREG32(SRBM_SOFT_RESET, SOFT_RESET_DMA | SOFT_RESET_DMA1);
1553 RREG32(SRBM_SOFT_RESET);
1554 udelay(50);
1555 WREG32(SRBM_SOFT_RESET, 0);
1556
1557 for (i = 0; i < 2; i++) {
1558 if (i == 0) {
1559 ring = &rdev->ring[R600_RING_TYPE_DMA_INDEX];
1560 reg_offset = DMA0_REGISTER_OFFSET;
1561 wb_offset = R600_WB_DMA_RPTR_OFFSET;
1562 } else {
1563 ring = &rdev->ring[CAYMAN_RING_TYPE_DMA1_INDEX];
1564 reg_offset = DMA1_REGISTER_OFFSET;
1565 wb_offset = CAYMAN_WB_DMA1_RPTR_OFFSET;
1566 }
1567
1568 WREG32(DMA_SEM_INCOMPLETE_TIMER_CNTL + reg_offset, 0);
1569 WREG32(DMA_SEM_WAIT_FAIL_TIMER_CNTL + reg_offset, 0);
1570
1571 /* Set ring buffer size in dwords */
1572 rb_bufsz = drm_order(ring->ring_size / 4);
1573 rb_cntl = rb_bufsz << 1;
1574#ifdef __BIG_ENDIAN
1575 rb_cntl |= DMA_RB_SWAP_ENABLE | DMA_RPTR_WRITEBACK_SWAP_ENABLE;
1576#endif
1577 WREG32(DMA_RB_CNTL + reg_offset, rb_cntl);
1578
1579 /* Initialize the ring buffer's read and write pointers */
1580 WREG32(DMA_RB_RPTR + reg_offset, 0);
1581 WREG32(DMA_RB_WPTR + reg_offset, 0);
1582
1583 /* set the wb address whether it's enabled or not */
1584 WREG32(DMA_RB_RPTR_ADDR_HI + reg_offset,
1585 upper_32_bits(rdev->wb.gpu_addr + wb_offset) & 0xFF);
1586 WREG32(DMA_RB_RPTR_ADDR_LO + reg_offset,
1587 ((rdev->wb.gpu_addr + wb_offset) & 0xFFFFFFFC));
1588
1589 if (rdev->wb.enabled)
1590 rb_cntl |= DMA_RPTR_WRITEBACK_ENABLE;
1591
1592 WREG32(DMA_RB_BASE + reg_offset, ring->gpu_addr >> 8);
1593
1594 /* enable DMA IBs */
Michel Dänzerb3dfcb22013-01-24 19:02:01 +01001595 ib_cntl = DMA_IB_ENABLE | CMD_VMID_FORCE;
1596#ifdef __BIG_ENDIAN
1597 ib_cntl |= DMA_IB_SWAP_ENABLE;
1598#endif
1599 WREG32(DMA_IB_CNTL + reg_offset, ib_cntl);
Alex Deucherf60cbd12012-12-04 15:27:33 -05001600
1601 dma_cntl = RREG32(DMA_CNTL + reg_offset);
1602 dma_cntl &= ~CTXEMPTY_INT_ENABLE;
1603 WREG32(DMA_CNTL + reg_offset, dma_cntl);
1604
1605 ring->wptr = 0;
1606 WREG32(DMA_RB_WPTR + reg_offset, ring->wptr << 2);
1607
1608 ring->rptr = RREG32(DMA_RB_RPTR + reg_offset) >> 2;
1609
1610 WREG32(DMA_RB_CNTL + reg_offset, rb_cntl | DMA_RB_ENABLE);
1611
1612 ring->ready = true;
1613
1614 r = radeon_ring_test(rdev, ring->idx, ring);
1615 if (r) {
1616 ring->ready = false;
1617 return r;
1618 }
1619 }
1620
1621 radeon_ttm_set_active_vram_size(rdev, rdev->mc.real_vram_size);
1622
1623 return 0;
1624}
1625
1626/**
1627 * cayman_dma_fini - tear down the async dma engines
1628 *
1629 * @rdev: radeon_device pointer
1630 *
1631 * Stop the async dma engines and free the rings (cayman-SI).
1632 */
1633void cayman_dma_fini(struct radeon_device *rdev)
1634{
1635 cayman_dma_stop(rdev);
1636 radeon_ring_fini(rdev, &rdev->ring[R600_RING_TYPE_DMA_INDEX]);
1637 radeon_ring_fini(rdev, &rdev->ring[CAYMAN_RING_TYPE_DMA1_INDEX]);
1638}
1639
Alex Deucher168757e2013-01-18 19:17:22 -05001640static u32 cayman_gpu_check_soft_reset(struct radeon_device *rdev)
1641{
1642 u32 reset_mask = 0;
1643 u32 tmp;
1644
1645 /* GRBM_STATUS */
1646 tmp = RREG32(GRBM_STATUS);
1647 if (tmp & (PA_BUSY | SC_BUSY |
1648 SH_BUSY | SX_BUSY |
1649 TA_BUSY | VGT_BUSY |
1650 DB_BUSY | CB_BUSY |
1651 GDS_BUSY | SPI_BUSY |
1652 IA_BUSY | IA_BUSY_NO_DMA))
1653 reset_mask |= RADEON_RESET_GFX;
1654
1655 if (tmp & (CF_RQ_PENDING | PF_RQ_PENDING |
1656 CP_BUSY | CP_COHERENCY_BUSY))
1657 reset_mask |= RADEON_RESET_CP;
1658
1659 if (tmp & GRBM_EE_BUSY)
1660 reset_mask |= RADEON_RESET_GRBM | RADEON_RESET_GFX | RADEON_RESET_CP;
1661
1662 /* DMA_STATUS_REG 0 */
1663 tmp = RREG32(DMA_STATUS_REG + DMA0_REGISTER_OFFSET);
1664 if (!(tmp & DMA_IDLE))
1665 reset_mask |= RADEON_RESET_DMA;
1666
1667 /* DMA_STATUS_REG 1 */
1668 tmp = RREG32(DMA_STATUS_REG + DMA1_REGISTER_OFFSET);
1669 if (!(tmp & DMA_IDLE))
1670 reset_mask |= RADEON_RESET_DMA1;
1671
1672 /* SRBM_STATUS2 */
1673 tmp = RREG32(SRBM_STATUS2);
1674 if (tmp & DMA_BUSY)
1675 reset_mask |= RADEON_RESET_DMA;
1676
1677 if (tmp & DMA1_BUSY)
1678 reset_mask |= RADEON_RESET_DMA1;
1679
1680 /* SRBM_STATUS */
1681 tmp = RREG32(SRBM_STATUS);
1682 if (tmp & (RLC_RQ_PENDING | RLC_BUSY))
1683 reset_mask |= RADEON_RESET_RLC;
1684
1685 if (tmp & IH_BUSY)
1686 reset_mask |= RADEON_RESET_IH;
1687
1688 if (tmp & SEM_BUSY)
1689 reset_mask |= RADEON_RESET_SEM;
1690
1691 if (tmp & GRBM_RQ_PENDING)
1692 reset_mask |= RADEON_RESET_GRBM;
1693
1694 if (tmp & VMC_BUSY)
1695 reset_mask |= RADEON_RESET_VMC;
1696
1697 if (tmp & (MCB_BUSY | MCB_NON_DISPLAY_BUSY |
1698 MCC_BUSY | MCD_BUSY))
1699 reset_mask |= RADEON_RESET_MC;
1700
1701 if (evergreen_is_display_hung(rdev))
1702 reset_mask |= RADEON_RESET_DISPLAY;
1703
1704 /* VM_L2_STATUS */
1705 tmp = RREG32(VM_L2_STATUS);
1706 if (tmp & L2_BUSY)
1707 reset_mask |= RADEON_RESET_VMC;
1708
Alex Deucherd808fc82013-02-28 10:03:08 -05001709 /* Skip MC reset as it's mostly likely not hung, just busy */
1710 if (reset_mask & RADEON_RESET_MC) {
1711 DRM_DEBUG("MC busy: 0x%08X, clearing.\n", reset_mask);
1712 reset_mask &= ~RADEON_RESET_MC;
1713 }
1714
Alex Deucher168757e2013-01-18 19:17:22 -05001715 return reset_mask;
1716}
1717
1718static void cayman_gpu_soft_reset(struct radeon_device *rdev, u32 reset_mask)
Alex Deucher271d6fe2013-01-03 12:48:05 -05001719{
1720 struct evergreen_mc_save save;
Alex Deucher187e3592013-01-18 14:51:38 -05001721 u32 grbm_soft_reset = 0, srbm_soft_reset = 0;
1722 u32 tmp;
Alex Deucher19fc42e2013-01-14 11:04:39 -05001723
Alex Deucher271d6fe2013-01-03 12:48:05 -05001724 if (reset_mask == 0)
Alex Deucher168757e2013-01-18 19:17:22 -05001725 return;
Alex Deucher271d6fe2013-01-03 12:48:05 -05001726
1727 dev_info(rdev->dev, "GPU softreset: 0x%08X\n", reset_mask);
1728
Alex Deucher187e3592013-01-18 14:51:38 -05001729 evergreen_print_gpu_status_regs(rdev);
Alex Deucher271d6fe2013-01-03 12:48:05 -05001730 dev_info(rdev->dev, " VM_CONTEXT0_PROTECTION_FAULT_ADDR 0x%08X\n",
1731 RREG32(0x14F8));
1732 dev_info(rdev->dev, " VM_CONTEXT0_PROTECTION_FAULT_STATUS 0x%08X\n",
1733 RREG32(0x14D8));
1734 dev_info(rdev->dev, " VM_CONTEXT1_PROTECTION_FAULT_ADDR 0x%08X\n",
1735 RREG32(0x14FC));
1736 dev_info(rdev->dev, " VM_CONTEXT1_PROTECTION_FAULT_STATUS 0x%08X\n",
1737 RREG32(0x14DC));
1738
Alex Deucher187e3592013-01-18 14:51:38 -05001739 /* Disable CP parsing/prefetching */
1740 WREG32(CP_ME_CNTL, CP_ME_HALT | CP_PFP_HALT);
1741
1742 if (reset_mask & RADEON_RESET_DMA) {
1743 /* dma0 */
1744 tmp = RREG32(DMA_RB_CNTL + DMA0_REGISTER_OFFSET);
1745 tmp &= ~DMA_RB_ENABLE;
1746 WREG32(DMA_RB_CNTL + DMA0_REGISTER_OFFSET, tmp);
Alex Deucher168757e2013-01-18 19:17:22 -05001747 }
Alex Deucher187e3592013-01-18 14:51:38 -05001748
Alex Deucher168757e2013-01-18 19:17:22 -05001749 if (reset_mask & RADEON_RESET_DMA1) {
Alex Deucher187e3592013-01-18 14:51:38 -05001750 /* dma1 */
1751 tmp = RREG32(DMA_RB_CNTL + DMA1_REGISTER_OFFSET);
1752 tmp &= ~DMA_RB_ENABLE;
1753 WREG32(DMA_RB_CNTL + DMA1_REGISTER_OFFSET, tmp);
1754 }
1755
Alex Deucher90fb8772013-01-23 18:59:17 -05001756 udelay(50);
1757
1758 evergreen_mc_stop(rdev, &save);
1759 if (evergreen_mc_wait_for_idle(rdev)) {
1760 dev_warn(rdev->dev, "Wait for MC idle timedout !\n");
1761 }
1762
Alex Deucher187e3592013-01-18 14:51:38 -05001763 if (reset_mask & (RADEON_RESET_GFX | RADEON_RESET_COMPUTE)) {
1764 grbm_soft_reset = SOFT_RESET_CB |
1765 SOFT_RESET_DB |
1766 SOFT_RESET_GDS |
1767 SOFT_RESET_PA |
1768 SOFT_RESET_SC |
1769 SOFT_RESET_SPI |
1770 SOFT_RESET_SH |
1771 SOFT_RESET_SX |
1772 SOFT_RESET_TC |
1773 SOFT_RESET_TA |
1774 SOFT_RESET_VGT |
1775 SOFT_RESET_IA;
1776 }
1777
1778 if (reset_mask & RADEON_RESET_CP) {
1779 grbm_soft_reset |= SOFT_RESET_CP | SOFT_RESET_VGT;
1780
1781 srbm_soft_reset |= SOFT_RESET_GRBM;
1782 }
Alex Deucher271d6fe2013-01-03 12:48:05 -05001783
1784 if (reset_mask & RADEON_RESET_DMA)
Alex Deucher168757e2013-01-18 19:17:22 -05001785 srbm_soft_reset |= SOFT_RESET_DMA;
1786
1787 if (reset_mask & RADEON_RESET_DMA1)
1788 srbm_soft_reset |= SOFT_RESET_DMA1;
1789
1790 if (reset_mask & RADEON_RESET_DISPLAY)
1791 srbm_soft_reset |= SOFT_RESET_DC;
1792
1793 if (reset_mask & RADEON_RESET_RLC)
1794 srbm_soft_reset |= SOFT_RESET_RLC;
1795
1796 if (reset_mask & RADEON_RESET_SEM)
1797 srbm_soft_reset |= SOFT_RESET_SEM;
1798
1799 if (reset_mask & RADEON_RESET_IH)
1800 srbm_soft_reset |= SOFT_RESET_IH;
1801
1802 if (reset_mask & RADEON_RESET_GRBM)
1803 srbm_soft_reset |= SOFT_RESET_GRBM;
1804
1805 if (reset_mask & RADEON_RESET_VMC)
1806 srbm_soft_reset |= SOFT_RESET_VMC;
1807
Alex Deucher24178ec2013-01-24 15:00:17 -05001808 if (!(rdev->flags & RADEON_IS_IGP)) {
1809 if (reset_mask & RADEON_RESET_MC)
1810 srbm_soft_reset |= SOFT_RESET_MC;
1811 }
Alex Deucher187e3592013-01-18 14:51:38 -05001812
1813 if (grbm_soft_reset) {
1814 tmp = RREG32(GRBM_SOFT_RESET);
1815 tmp |= grbm_soft_reset;
1816 dev_info(rdev->dev, "GRBM_SOFT_RESET=0x%08X\n", tmp);
1817 WREG32(GRBM_SOFT_RESET, tmp);
1818 tmp = RREG32(GRBM_SOFT_RESET);
1819
1820 udelay(50);
1821
1822 tmp &= ~grbm_soft_reset;
1823 WREG32(GRBM_SOFT_RESET, tmp);
1824 tmp = RREG32(GRBM_SOFT_RESET);
1825 }
1826
1827 if (srbm_soft_reset) {
1828 tmp = RREG32(SRBM_SOFT_RESET);
1829 tmp |= srbm_soft_reset;
1830 dev_info(rdev->dev, "SRBM_SOFT_RESET=0x%08X\n", tmp);
1831 WREG32(SRBM_SOFT_RESET, tmp);
1832 tmp = RREG32(SRBM_SOFT_RESET);
1833
1834 udelay(50);
1835
1836 tmp &= ~srbm_soft_reset;
1837 WREG32(SRBM_SOFT_RESET, tmp);
1838 tmp = RREG32(SRBM_SOFT_RESET);
1839 }
Alex Deucher271d6fe2013-01-03 12:48:05 -05001840
1841 /* Wait a little for things to settle down */
1842 udelay(50);
1843
Alex Deucherb9952a82011-03-02 20:07:33 -05001844 evergreen_mc_resume(rdev, &save);
Alex Deucher187e3592013-01-18 14:51:38 -05001845 udelay(50);
Alex Deucher410a3412013-01-18 13:05:39 -05001846
Alex Deucher187e3592013-01-18 14:51:38 -05001847 evergreen_print_gpu_status_regs(rdev);
Alex Deucherb9952a82011-03-02 20:07:33 -05001848}
1849
1850int cayman_asic_reset(struct radeon_device *rdev)
1851{
Alex Deucher168757e2013-01-18 19:17:22 -05001852 u32 reset_mask;
1853
1854 reset_mask = cayman_gpu_check_soft_reset(rdev);
1855
1856 if (reset_mask)
1857 r600_set_bios_scratch_engine_hung(rdev, true);
1858
1859 cayman_gpu_soft_reset(rdev, reset_mask);
1860
1861 reset_mask = cayman_gpu_check_soft_reset(rdev);
1862
1863 if (!reset_mask)
1864 r600_set_bios_scratch_engine_hung(rdev, false);
1865
1866 return 0;
Alex Deucherb9952a82011-03-02 20:07:33 -05001867}
1868
Alex Deucherf60cbd12012-12-04 15:27:33 -05001869/**
Alex Deucher123bc182013-01-24 11:37:19 -05001870 * cayman_gfx_is_lockup - Check if the GFX engine is locked up
1871 *
1872 * @rdev: radeon_device pointer
1873 * @ring: radeon_ring structure holding ring information
1874 *
1875 * Check if the GFX engine is locked up.
1876 * Returns true if the engine appears to be locked up, false if not.
1877 */
1878bool cayman_gfx_is_lockup(struct radeon_device *rdev, struct radeon_ring *ring)
1879{
1880 u32 reset_mask = cayman_gpu_check_soft_reset(rdev);
1881
1882 if (!(reset_mask & (RADEON_RESET_GFX |
1883 RADEON_RESET_COMPUTE |
1884 RADEON_RESET_CP))) {
1885 radeon_ring_lockup_update(ring);
1886 return false;
1887 }
1888 /* force CP activities */
1889 radeon_ring_force_activity(rdev, ring);
1890 return radeon_ring_test_lockup(rdev, ring);
1891}
1892
1893/**
Alex Deucherf60cbd12012-12-04 15:27:33 -05001894 * cayman_dma_is_lockup - Check if the DMA engine is locked up
1895 *
1896 * @rdev: radeon_device pointer
1897 * @ring: radeon_ring structure holding ring information
1898 *
Alex Deucher123bc182013-01-24 11:37:19 -05001899 * Check if the async DMA engine is locked up.
Alex Deucherf60cbd12012-12-04 15:27:33 -05001900 * Returns true if the engine appears to be locked up, false if not.
1901 */
1902bool cayman_dma_is_lockup(struct radeon_device *rdev, struct radeon_ring *ring)
1903{
Alex Deucher123bc182013-01-24 11:37:19 -05001904 u32 reset_mask = cayman_gpu_check_soft_reset(rdev);
1905 u32 mask;
Alex Deucherf60cbd12012-12-04 15:27:33 -05001906
1907 if (ring->idx == R600_RING_TYPE_DMA_INDEX)
Alex Deucher123bc182013-01-24 11:37:19 -05001908 mask = RADEON_RESET_DMA;
Alex Deucherf60cbd12012-12-04 15:27:33 -05001909 else
Alex Deucher123bc182013-01-24 11:37:19 -05001910 mask = RADEON_RESET_DMA1;
1911
1912 if (!(reset_mask & mask)) {
Alex Deucherf60cbd12012-12-04 15:27:33 -05001913 radeon_ring_lockup_update(ring);
1914 return false;
1915 }
1916 /* force ring activities */
1917 radeon_ring_force_activity(rdev, ring);
1918 return radeon_ring_test_lockup(rdev, ring);
1919}
1920
Alex Deucher755d8192011-03-02 20:07:34 -05001921static int cayman_startup(struct radeon_device *rdev)
1922{
Christian Könige32eb502011-10-23 12:56:27 +02001923 struct radeon_ring *ring = &rdev->ring[RADEON_RING_TYPE_GFX_INDEX];
Alex Deucher755d8192011-03-02 20:07:34 -05001924 int r;
1925
Ilija Hadzicb07759b2011-09-20 10:22:58 -04001926 /* enable pcie gen2 link */
1927 evergreen_pcie_gen2_enable(rdev);
1928
Alex Deucherc420c742012-03-20 17:18:39 -04001929 if (rdev->flags & RADEON_IS_IGP) {
1930 if (!rdev->me_fw || !rdev->pfp_fw || !rdev->rlc_fw) {
1931 r = ni_init_microcode(rdev);
1932 if (r) {
1933 DRM_ERROR("Failed to load firmware!\n");
1934 return r;
1935 }
1936 }
1937 } else {
1938 if (!rdev->me_fw || !rdev->pfp_fw || !rdev->rlc_fw || !rdev->mc_fw) {
1939 r = ni_init_microcode(rdev);
1940 if (r) {
1941 DRM_ERROR("Failed to load firmware!\n");
1942 return r;
1943 }
1944 }
1945
1946 r = ni_mc_load_microcode(rdev);
Alex Deucher755d8192011-03-02 20:07:34 -05001947 if (r) {
Alex Deucherc420c742012-03-20 17:18:39 -04001948 DRM_ERROR("Failed to load MC firmware!\n");
Alex Deucher755d8192011-03-02 20:07:34 -05001949 return r;
1950 }
1951 }
Alex Deucher755d8192011-03-02 20:07:34 -05001952
Alex Deucher16cdf042011-10-28 10:30:02 -04001953 r = r600_vram_scratch_init(rdev);
1954 if (r)
1955 return r;
1956
Alex Deucher755d8192011-03-02 20:07:34 -05001957 evergreen_mc_program(rdev);
1958 r = cayman_pcie_gart_enable(rdev);
1959 if (r)
1960 return r;
1961 cayman_gpu_init(rdev);
1962
Alex Deuchercb92d452011-05-25 16:39:00 -04001963 r = evergreen_blit_init(rdev);
Alex Deucher755d8192011-03-02 20:07:34 -05001964 if (r) {
Ilija Hadzicfb3d9e92011-10-12 23:29:41 -04001965 r600_blit_fini(rdev);
Alex Deucher27cd7762012-02-23 17:53:42 -05001966 rdev->asic->copy.copy = NULL;
Alex Deucher755d8192011-03-02 20:07:34 -05001967 dev_warn(rdev->dev, "failed blitter (%d) falling back to memcpy\n", r);
1968 }
Alex Deucher755d8192011-03-02 20:07:34 -05001969
Alex Deucherc420c742012-03-20 17:18:39 -04001970 /* allocate rlc buffers */
1971 if (rdev->flags & RADEON_IS_IGP) {
1972 r = si_rlc_init(rdev);
1973 if (r) {
1974 DRM_ERROR("Failed to init rlc BOs!\n");
1975 return r;
1976 }
1977 }
1978
Alex Deucher755d8192011-03-02 20:07:34 -05001979 /* allocate wb buffer */
1980 r = radeon_wb_init(rdev);
1981 if (r)
1982 return r;
1983
Jerome Glisse30eb77f2011-11-20 20:45:34 +00001984 r = radeon_fence_driver_start_ring(rdev, RADEON_RING_TYPE_GFX_INDEX);
1985 if (r) {
1986 dev_err(rdev->dev, "failed initializing CP fences (%d).\n", r);
1987 return r;
1988 }
1989
Christian Königf2ba57b2013-04-08 12:41:29 +02001990 r = rv770_uvd_resume(rdev);
1991 if (!r) {
1992 r = radeon_fence_driver_start_ring(rdev,
1993 R600_RING_TYPE_UVD_INDEX);
1994 if (r)
1995 dev_err(rdev->dev, "UVD fences init error (%d).\n", r);
1996 }
1997 if (r)
1998 rdev->ring[R600_RING_TYPE_UVD_INDEX].ring_size = 0;
1999
Jerome Glisse30eb77f2011-11-20 20:45:34 +00002000 r = radeon_fence_driver_start_ring(rdev, CAYMAN_RING_TYPE_CP1_INDEX);
2001 if (r) {
2002 dev_err(rdev->dev, "failed initializing CP fences (%d).\n", r);
2003 return r;
2004 }
2005
2006 r = radeon_fence_driver_start_ring(rdev, CAYMAN_RING_TYPE_CP2_INDEX);
2007 if (r) {
2008 dev_err(rdev->dev, "failed initializing CP fences (%d).\n", r);
2009 return r;
2010 }
2011
Alex Deucherf60cbd12012-12-04 15:27:33 -05002012 r = radeon_fence_driver_start_ring(rdev, R600_RING_TYPE_DMA_INDEX);
2013 if (r) {
2014 dev_err(rdev->dev, "failed initializing DMA fences (%d).\n", r);
2015 return r;
2016 }
2017
2018 r = radeon_fence_driver_start_ring(rdev, CAYMAN_RING_TYPE_DMA1_INDEX);
2019 if (r) {
2020 dev_err(rdev->dev, "failed initializing DMA fences (%d).\n", r);
2021 return r;
2022 }
2023
Alex Deucher755d8192011-03-02 20:07:34 -05002024 /* Enable IRQ */
Adis Hamziće49f3952013-06-02 16:47:54 +02002025 if (!rdev->irq.installed) {
2026 r = radeon_irq_kms_init(rdev);
2027 if (r)
2028 return r;
2029 }
2030
Alex Deucher755d8192011-03-02 20:07:34 -05002031 r = r600_irq_init(rdev);
2032 if (r) {
2033 DRM_ERROR("radeon: IH init failed (%d).\n", r);
2034 radeon_irq_kms_fini(rdev);
2035 return r;
2036 }
2037 evergreen_irq_set(rdev);
2038
Christian Könige32eb502011-10-23 12:56:27 +02002039 r = radeon_ring_init(rdev, ring, ring->ring_size, RADEON_WB_CP_RPTR_OFFSET,
Alex Deucher78c55602011-11-17 14:25:56 -05002040 CP_RB0_RPTR, CP_RB0_WPTR,
2041 0, 0xfffff, RADEON_CP_PACKET2);
Alex Deucher755d8192011-03-02 20:07:34 -05002042 if (r)
2043 return r;
Alex Deucherf60cbd12012-12-04 15:27:33 -05002044
2045 ring = &rdev->ring[R600_RING_TYPE_DMA_INDEX];
2046 r = radeon_ring_init(rdev, ring, ring->ring_size, R600_WB_DMA_RPTR_OFFSET,
2047 DMA_RB_RPTR + DMA0_REGISTER_OFFSET,
2048 DMA_RB_WPTR + DMA0_REGISTER_OFFSET,
2049 2, 0x3fffc, DMA_PACKET(DMA_PACKET_NOP, 0, 0, 0));
2050 if (r)
2051 return r;
2052
2053 ring = &rdev->ring[CAYMAN_RING_TYPE_DMA1_INDEX];
2054 r = radeon_ring_init(rdev, ring, ring->ring_size, CAYMAN_WB_DMA1_RPTR_OFFSET,
2055 DMA_RB_RPTR + DMA1_REGISTER_OFFSET,
2056 DMA_RB_WPTR + DMA1_REGISTER_OFFSET,
2057 2, 0x3fffc, DMA_PACKET(DMA_PACKET_NOP, 0, 0, 0));
2058 if (r)
2059 return r;
2060
Alex Deucher755d8192011-03-02 20:07:34 -05002061 r = cayman_cp_load_microcode(rdev);
2062 if (r)
2063 return r;
2064 r = cayman_cp_resume(rdev);
2065 if (r)
2066 return r;
2067
Alex Deucherf60cbd12012-12-04 15:27:33 -05002068 r = cayman_dma_resume(rdev);
2069 if (r)
2070 return r;
2071
Christian Königf2ba57b2013-04-08 12:41:29 +02002072 ring = &rdev->ring[R600_RING_TYPE_UVD_INDEX];
2073 if (ring->ring_size) {
2074 r = radeon_ring_init(rdev, ring, ring->ring_size,
2075 R600_WB_UVD_RPTR_OFFSET,
2076 UVD_RBC_RB_RPTR, UVD_RBC_RB_WPTR,
2077 0, 0xfffff, RADEON_CP_PACKET2);
2078 if (!r)
2079 r = r600_uvd_init(rdev);
2080 if (r)
2081 DRM_ERROR("radeon: failed initializing UVD (%d).\n", r);
2082 }
2083
Christian König2898c342012-07-05 11:55:34 +02002084 r = radeon_ib_pool_init(rdev);
2085 if (r) {
2086 dev_err(rdev->dev, "IB initialization failed (%d).\n", r);
Jerome Glisseb15ba512011-11-15 11:48:34 -05002087 return r;
Christian König2898c342012-07-05 11:55:34 +02002088 }
Jerome Glisseb15ba512011-11-15 11:48:34 -05002089
Christian Königc6105f22012-07-05 14:32:00 +02002090 r = radeon_vm_manager_init(rdev);
2091 if (r) {
2092 dev_err(rdev->dev, "vm manager initialization failed (%d).\n", r);
Jerome Glisse721604a2012-01-05 22:11:05 -05002093 return r;
Christian Königc6105f22012-07-05 14:32:00 +02002094 }
Jerome Glisse721604a2012-01-05 22:11:05 -05002095
Rafał Miłecki6b53a052012-06-11 12:34:01 +02002096 r = r600_audio_init(rdev);
2097 if (r)
2098 return r;
2099
Alex Deucher755d8192011-03-02 20:07:34 -05002100 return 0;
2101}
2102
2103int cayman_resume(struct radeon_device *rdev)
2104{
2105 int r;
2106
2107 /* Do not reset GPU before posting, on rv770 hw unlike on r500 hw,
2108 * posting will perform necessary task to bring back GPU into good
2109 * shape.
2110 */
2111 /* post card */
2112 atom_asic_init(rdev->mode_info.atom_context);
2113
Alex Deuchera2c96a22013-02-28 17:58:36 -05002114 /* init golden registers */
2115 ni_init_golden_registers(rdev);
2116
Jerome Glisseb15ba512011-11-15 11:48:34 -05002117 rdev->accel_working = true;
Alex Deucher755d8192011-03-02 20:07:34 -05002118 r = cayman_startup(rdev);
2119 if (r) {
2120 DRM_ERROR("cayman startup failed on resume\n");
Jerome Glisse6b7746e2012-02-20 17:57:20 -05002121 rdev->accel_working = false;
Alex Deucher755d8192011-03-02 20:07:34 -05002122 return r;
2123 }
Alex Deucher755d8192011-03-02 20:07:34 -05002124 return r;
Alex Deucher755d8192011-03-02 20:07:34 -05002125}
2126
2127int cayman_suspend(struct radeon_device *rdev)
2128{
Rafał Miłecki6b53a052012-06-11 12:34:01 +02002129 r600_audio_fini(rdev);
Alex Deucherfa3daf92013-03-11 15:32:26 -04002130 radeon_vm_manager_fini(rdev);
Alex Deucher755d8192011-03-02 20:07:34 -05002131 cayman_cp_enable(rdev, false);
Alex Deucherf60cbd12012-12-04 15:27:33 -05002132 cayman_dma_stop(rdev);
Christian Königf2ba57b2013-04-08 12:41:29 +02002133 r600_uvd_rbc_stop(rdev);
2134 radeon_uvd_suspend(rdev);
Alex Deucher755d8192011-03-02 20:07:34 -05002135 evergreen_irq_suspend(rdev);
2136 radeon_wb_disable(rdev);
2137 cayman_pcie_gart_disable(rdev);
Alex Deucher755d8192011-03-02 20:07:34 -05002138 return 0;
2139}
2140
2141/* Plan is to move initialization in that function and use
2142 * helper function so that radeon_device_init pretty much
2143 * do nothing more than calling asic specific function. This
2144 * should also allow to remove a bunch of callback function
2145 * like vram_info.
2146 */
2147int cayman_init(struct radeon_device *rdev)
2148{
Christian Könige32eb502011-10-23 12:56:27 +02002149 struct radeon_ring *ring = &rdev->ring[RADEON_RING_TYPE_GFX_INDEX];
Alex Deucher755d8192011-03-02 20:07:34 -05002150 int r;
2151
Alex Deucher755d8192011-03-02 20:07:34 -05002152 /* Read BIOS */
2153 if (!radeon_get_bios(rdev)) {
2154 if (ASIC_IS_AVIVO(rdev))
2155 return -EINVAL;
2156 }
2157 /* Must be an ATOMBIOS */
2158 if (!rdev->is_atom_bios) {
2159 dev_err(rdev->dev, "Expecting atombios for cayman GPU\n");
2160 return -EINVAL;
2161 }
2162 r = radeon_atombios_init(rdev);
2163 if (r)
2164 return r;
2165
2166 /* Post card if necessary */
2167 if (!radeon_card_posted(rdev)) {
2168 if (!rdev->bios) {
2169 dev_err(rdev->dev, "Card not posted and no BIOS - ignoring\n");
2170 return -EINVAL;
2171 }
2172 DRM_INFO("GPU not posted. posting now...\n");
2173 atom_asic_init(rdev->mode_info.atom_context);
2174 }
Alex Deuchera2c96a22013-02-28 17:58:36 -05002175 /* init golden registers */
2176 ni_init_golden_registers(rdev);
Alex Deucher755d8192011-03-02 20:07:34 -05002177 /* Initialize scratch registers */
2178 r600_scratch_init(rdev);
2179 /* Initialize surface registers */
2180 radeon_surface_init(rdev);
2181 /* Initialize clocks */
2182 radeon_get_clock_info(rdev->ddev);
2183 /* Fence driver */
Jerome Glisse30eb77f2011-11-20 20:45:34 +00002184 r = radeon_fence_driver_init(rdev);
Alex Deucher755d8192011-03-02 20:07:34 -05002185 if (r)
2186 return r;
2187 /* initialize memory controller */
2188 r = evergreen_mc_init(rdev);
2189 if (r)
2190 return r;
2191 /* Memory manager */
2192 r = radeon_bo_init(rdev);
2193 if (r)
2194 return r;
2195
Christian Könige32eb502011-10-23 12:56:27 +02002196 ring->ring_obj = NULL;
2197 r600_ring_init(rdev, ring, 1024 * 1024);
Alex Deucher755d8192011-03-02 20:07:34 -05002198
Alex Deucherf60cbd12012-12-04 15:27:33 -05002199 ring = &rdev->ring[R600_RING_TYPE_DMA_INDEX];
2200 ring->ring_obj = NULL;
2201 r600_ring_init(rdev, ring, 64 * 1024);
2202
2203 ring = &rdev->ring[CAYMAN_RING_TYPE_DMA1_INDEX];
2204 ring->ring_obj = NULL;
2205 r600_ring_init(rdev, ring, 64 * 1024);
2206
Christian Königf2ba57b2013-04-08 12:41:29 +02002207 r = radeon_uvd_init(rdev);
2208 if (!r) {
2209 ring = &rdev->ring[R600_RING_TYPE_UVD_INDEX];
2210 ring->ring_obj = NULL;
2211 r600_ring_init(rdev, ring, 4096);
2212 }
2213
Alex Deucher755d8192011-03-02 20:07:34 -05002214 rdev->ih.ring_obj = NULL;
2215 r600_ih_ring_init(rdev, 64 * 1024);
2216
2217 r = r600_pcie_gart_init(rdev);
2218 if (r)
2219 return r;
2220
2221 rdev->accel_working = true;
2222 r = cayman_startup(rdev);
2223 if (r) {
2224 dev_err(rdev->dev, "disabling GPU acceleration\n");
2225 cayman_cp_fini(rdev);
Alex Deucherf60cbd12012-12-04 15:27:33 -05002226 cayman_dma_fini(rdev);
Alex Deucher755d8192011-03-02 20:07:34 -05002227 r600_irq_fini(rdev);
Alex Deucherc420c742012-03-20 17:18:39 -04002228 if (rdev->flags & RADEON_IS_IGP)
2229 si_rlc_fini(rdev);
Alex Deucher755d8192011-03-02 20:07:34 -05002230 radeon_wb_fini(rdev);
Christian König2898c342012-07-05 11:55:34 +02002231 radeon_ib_pool_fini(rdev);
Jerome Glisse721604a2012-01-05 22:11:05 -05002232 radeon_vm_manager_fini(rdev);
Alex Deucher755d8192011-03-02 20:07:34 -05002233 radeon_irq_kms_fini(rdev);
2234 cayman_pcie_gart_fini(rdev);
2235 rdev->accel_working = false;
2236 }
Alex Deucher755d8192011-03-02 20:07:34 -05002237
2238 /* Don't start up if the MC ucode is missing.
2239 * The default clocks and voltages before the MC ucode
2240 * is loaded are not suffient for advanced operations.
Alex Deucherc420c742012-03-20 17:18:39 -04002241 *
2242 * We can skip this check for TN, because there is no MC
2243 * ucode.
Alex Deucher755d8192011-03-02 20:07:34 -05002244 */
Alex Deucherc420c742012-03-20 17:18:39 -04002245 if (!rdev->mc_fw && !(rdev->flags & RADEON_IS_IGP)) {
Alex Deucher755d8192011-03-02 20:07:34 -05002246 DRM_ERROR("radeon: MC ucode required for NI+.\n");
2247 return -EINVAL;
2248 }
2249
2250 return 0;
2251}
2252
2253void cayman_fini(struct radeon_device *rdev)
2254{
Ilija Hadzicfb3d9e92011-10-12 23:29:41 -04002255 r600_blit_fini(rdev);
Alex Deucher755d8192011-03-02 20:07:34 -05002256 cayman_cp_fini(rdev);
Alex Deucherf60cbd12012-12-04 15:27:33 -05002257 cayman_dma_fini(rdev);
Alex Deucher755d8192011-03-02 20:07:34 -05002258 r600_irq_fini(rdev);
Alex Deucherc420c742012-03-20 17:18:39 -04002259 if (rdev->flags & RADEON_IS_IGP)
2260 si_rlc_fini(rdev);
Alex Deucher755d8192011-03-02 20:07:34 -05002261 radeon_wb_fini(rdev);
Jerome Glisse721604a2012-01-05 22:11:05 -05002262 radeon_vm_manager_fini(rdev);
Christian König2898c342012-07-05 11:55:34 +02002263 radeon_ib_pool_fini(rdev);
Alex Deucher755d8192011-03-02 20:07:34 -05002264 radeon_irq_kms_fini(rdev);
Christian Königf2ba57b2013-04-08 12:41:29 +02002265 radeon_uvd_fini(rdev);
Alex Deucher755d8192011-03-02 20:07:34 -05002266 cayman_pcie_gart_fini(rdev);
Alex Deucher16cdf042011-10-28 10:30:02 -04002267 r600_vram_scratch_fini(rdev);
Alex Deucher755d8192011-03-02 20:07:34 -05002268 radeon_gem_fini(rdev);
2269 radeon_fence_driver_fini(rdev);
2270 radeon_bo_fini(rdev);
2271 radeon_atombios_fini(rdev);
2272 kfree(rdev->bios);
2273 rdev->bios = NULL;
2274}
2275
Jerome Glisse721604a2012-01-05 22:11:05 -05002276/*
2277 * vm
2278 */
2279int cayman_vm_init(struct radeon_device *rdev)
2280{
2281 /* number of VMs */
2282 rdev->vm_manager.nvm = 8;
2283 /* base offset of vram pages */
Alex Deuchere71270f2012-03-20 17:18:38 -04002284 if (rdev->flags & RADEON_IS_IGP) {
2285 u64 tmp = RREG32(FUS_MC_VM_FB_OFFSET);
2286 tmp <<= 22;
2287 rdev->vm_manager.vram_base_offset = tmp;
2288 } else
2289 rdev->vm_manager.vram_base_offset = 0;
Jerome Glisse721604a2012-01-05 22:11:05 -05002290 return 0;
2291}
2292
2293void cayman_vm_fini(struct radeon_device *rdev)
2294{
2295}
2296
Christian Königdce34bf2012-09-17 19:36:18 +02002297#define R600_ENTRY_VALID (1 << 0)
Jerome Glisse721604a2012-01-05 22:11:05 -05002298#define R600_PTE_SYSTEM (1 << 1)
2299#define R600_PTE_SNOOPED (1 << 2)
2300#define R600_PTE_READABLE (1 << 5)
2301#define R600_PTE_WRITEABLE (1 << 6)
2302
Christian König089a7862012-08-11 11:54:05 +02002303uint32_t cayman_vm_page_flags(struct radeon_device *rdev, uint32_t flags)
Jerome Glisse721604a2012-01-05 22:11:05 -05002304{
2305 uint32_t r600_flags = 0;
Christian Königdce34bf2012-09-17 19:36:18 +02002306 r600_flags |= (flags & RADEON_VM_PAGE_VALID) ? R600_ENTRY_VALID : 0;
Jerome Glisse721604a2012-01-05 22:11:05 -05002307 r600_flags |= (flags & RADEON_VM_PAGE_READABLE) ? R600_PTE_READABLE : 0;
2308 r600_flags |= (flags & RADEON_VM_PAGE_WRITEABLE) ? R600_PTE_WRITEABLE : 0;
2309 if (flags & RADEON_VM_PAGE_SYSTEM) {
2310 r600_flags |= R600_PTE_SYSTEM;
2311 r600_flags |= (flags & RADEON_VM_PAGE_SNOOPED) ? R600_PTE_SNOOPED : 0;
2312 }
2313 return r600_flags;
2314}
2315
Alex Deucher7a083292012-08-31 13:51:21 -04002316/**
2317 * cayman_vm_set_page - update the page tables using the CP
2318 *
2319 * @rdev: radeon_device pointer
Alex Deucher43f12142013-02-01 17:32:42 +01002320 * @ib: indirect buffer to fill with commands
Christian Königdce34bf2012-09-17 19:36:18 +02002321 * @pe: addr of the page entry
2322 * @addr: dst addr to write into pe
2323 * @count: number of page entries to update
2324 * @incr: increase next addr by incr bytes
2325 * @flags: access flags
Alex Deucher7a083292012-08-31 13:51:21 -04002326 *
Alex Deucher43f12142013-02-01 17:32:42 +01002327 * Update the page tables using the CP (cayman/TN).
Alex Deucher7a083292012-08-31 13:51:21 -04002328 */
Alex Deucher43f12142013-02-01 17:32:42 +01002329void cayman_vm_set_page(struct radeon_device *rdev,
2330 struct radeon_ib *ib,
2331 uint64_t pe,
Christian Königdce34bf2012-09-17 19:36:18 +02002332 uint64_t addr, unsigned count,
2333 uint32_t incr, uint32_t flags)
Jerome Glisse721604a2012-01-05 22:11:05 -05002334{
Christian Königdce34bf2012-09-17 19:36:18 +02002335 uint32_t r600_flags = cayman_vm_page_flags(rdev, flags);
Alex Deucher3b6b59b2012-10-22 12:19:01 -04002336 uint64_t value;
2337 unsigned ndw;
Jerome Glisse721604a2012-01-05 22:11:05 -05002338
Alex Deucher3b6b59b2012-10-22 12:19:01 -04002339 if (rdev->asic->vm.pt_ring_index == RADEON_RING_TYPE_GFX_INDEX) {
2340 while (count) {
2341 ndw = 1 + count * 2;
2342 if (ndw > 0x3FFF)
2343 ndw = 0x3FFF;
Christian König089a7862012-08-11 11:54:05 +02002344
Alex Deucher43f12142013-02-01 17:32:42 +01002345 ib->ptr[ib->length_dw++] = PACKET3(PACKET3_ME_WRITE, ndw);
2346 ib->ptr[ib->length_dw++] = pe;
2347 ib->ptr[ib->length_dw++] = upper_32_bits(pe) & 0xff;
Alex Deucher3b6b59b2012-10-22 12:19:01 -04002348 for (; ndw > 1; ndw -= 2, --count, pe += 8) {
2349 if (flags & RADEON_VM_PAGE_SYSTEM) {
2350 value = radeon_vm_map_gart(rdev, addr);
2351 value &= 0xFFFFFFFFFFFFF000ULL;
2352 } else if (flags & RADEON_VM_PAGE_VALID) {
2353 value = addr;
2354 } else {
2355 value = 0;
2356 }
Christian Königf9fdffa2012-10-22 17:42:36 +02002357 addr += incr;
Alex Deucher3b6b59b2012-10-22 12:19:01 -04002358 value |= r600_flags;
Alex Deucher43f12142013-02-01 17:32:42 +01002359 ib->ptr[ib->length_dw++] = value;
2360 ib->ptr[ib->length_dw++] = upper_32_bits(value);
Christian Königf9fdffa2012-10-22 17:42:36 +02002361 }
Alex Deucher3b6b59b2012-10-22 12:19:01 -04002362 }
2363 } else {
Alex Deucher2ab91ad2013-04-16 10:42:15 -04002364 if ((flags & RADEON_VM_PAGE_SYSTEM) ||
2365 (count == 1)) {
2366 while (count) {
2367 ndw = count * 2;
2368 if (ndw > 0xFFFFE)
2369 ndw = 0xFFFFE;
Christian Königf9fdffa2012-10-22 17:42:36 +02002370
Alex Deucher2ab91ad2013-04-16 10:42:15 -04002371 /* for non-physically contiguous pages (system) */
2372 ib->ptr[ib->length_dw++] = DMA_PACKET(DMA_PACKET_WRITE, 0, 0, ndw);
2373 ib->ptr[ib->length_dw++] = pe;
2374 ib->ptr[ib->length_dw++] = upper_32_bits(pe) & 0xff;
2375 for (; ndw > 0; ndw -= 2, --count, pe += 8) {
2376 if (flags & RADEON_VM_PAGE_SYSTEM) {
2377 value = radeon_vm_map_gart(rdev, addr);
2378 value &= 0xFFFFFFFFFFFFF000ULL;
2379 } else if (flags & RADEON_VM_PAGE_VALID) {
2380 value = addr;
2381 } else {
2382 value = 0;
2383 }
2384 addr += incr;
2385 value |= r600_flags;
2386 ib->ptr[ib->length_dw++] = value;
2387 ib->ptr[ib->length_dw++] = upper_32_bits(value);
Alex Deucher3b6b59b2012-10-22 12:19:01 -04002388 }
Alex Deucher2ab91ad2013-04-16 10:42:15 -04002389 }
2390 while (ib->length_dw & 0x7)
2391 ib->ptr[ib->length_dw++] = DMA_PACKET(DMA_PACKET_NOP, 0, 0, 0);
2392 } else {
2393 while (count) {
2394 ndw = count * 2;
2395 if (ndw > 0xFFFFE)
2396 ndw = 0xFFFFE;
2397
2398 if (flags & RADEON_VM_PAGE_VALID)
2399 value = addr;
2400 else
2401 value = 0;
2402 /* for physically contiguous pages (vram) */
2403 ib->ptr[ib->length_dw++] = DMA_PTE_PDE_PACKET(ndw);
2404 ib->ptr[ib->length_dw++] = pe; /* dst addr */
2405 ib->ptr[ib->length_dw++] = upper_32_bits(pe) & 0xff;
2406 ib->ptr[ib->length_dw++] = r600_flags; /* mask */
2407 ib->ptr[ib->length_dw++] = 0;
2408 ib->ptr[ib->length_dw++] = value; /* value */
Alex Deucher43f12142013-02-01 17:32:42 +01002409 ib->ptr[ib->length_dw++] = upper_32_bits(value);
Alex Deucher2ab91ad2013-04-16 10:42:15 -04002410 ib->ptr[ib->length_dw++] = incr; /* increment size */
2411 ib->ptr[ib->length_dw++] = 0;
2412 pe += ndw * 4;
2413 addr += (ndw / 2) * incr;
2414 count -= ndw / 2;
Alex Deucher3b6b59b2012-10-22 12:19:01 -04002415 }
Christian König2a6f1ab2012-08-11 15:00:30 +02002416 }
Alex Deucher43f12142013-02-01 17:32:42 +01002417 while (ib->length_dw & 0x7)
2418 ib->ptr[ib->length_dw++] = DMA_PACKET(DMA_PACKET_NOP, 0, 0, 0);
Christian König2a6f1ab2012-08-11 15:00:30 +02002419 }
Jerome Glisse721604a2012-01-05 22:11:05 -05002420}
Christian König9b40e5d2012-08-08 12:22:43 +02002421
Alex Deucher7a083292012-08-31 13:51:21 -04002422/**
2423 * cayman_vm_flush - vm flush using the CP
2424 *
2425 * @rdev: radeon_device pointer
2426 *
2427 * Update the page table base and flush the VM TLB
2428 * using the CP (cayman-si).
2429 */
Alex Deucher498522b2012-10-02 14:43:38 -04002430void cayman_vm_flush(struct radeon_device *rdev, int ridx, struct radeon_vm *vm)
Christian König9b40e5d2012-08-08 12:22:43 +02002431{
Alex Deucher498522b2012-10-02 14:43:38 -04002432 struct radeon_ring *ring = &rdev->ring[ridx];
Christian König9b40e5d2012-08-08 12:22:43 +02002433
Christian Königee60e292012-08-09 16:21:08 +02002434 if (vm == NULL)
Christian König9b40e5d2012-08-08 12:22:43 +02002435 return;
2436
Christian Königee60e292012-08-09 16:21:08 +02002437 radeon_ring_write(ring, PACKET0(VM_CONTEXT0_PAGE_TABLE_BASE_ADDR + (vm->id << 2), 0));
Dmitry Cherkasovfa87e622012-09-17 19:36:19 +02002438 radeon_ring_write(ring, vm->pd_gpu_addr >> 12);
Christian Königee60e292012-08-09 16:21:08 +02002439
Christian König9b40e5d2012-08-08 12:22:43 +02002440 /* flush hdp cache */
2441 radeon_ring_write(ring, PACKET0(HDP_MEM_COHERENCY_FLUSH_CNTL, 0));
2442 radeon_ring_write(ring, 0x1);
2443
2444 /* bits 0-7 are the VM contexts0-7 */
2445 radeon_ring_write(ring, PACKET0(VM_INVALIDATE_REQUEST, 0));
Alex Deucher498522b2012-10-02 14:43:38 -04002446 radeon_ring_write(ring, 1 << vm->id);
Christian König58f8cf52012-10-22 17:42:35 +02002447
2448 /* sync PFP to ME, otherwise we might get invalid PFP reads */
2449 radeon_ring_write(ring, PACKET3(PACKET3_PFP_SYNC_ME, 0));
2450 radeon_ring_write(ring, 0x0);
Alex Deucher0af62b02011-01-06 21:19:31 -05002451}
Alex Deucherf60cbd12012-12-04 15:27:33 -05002452
2453void cayman_dma_vm_flush(struct radeon_device *rdev, int ridx, struct radeon_vm *vm)
2454{
2455 struct radeon_ring *ring = &rdev->ring[ridx];
2456
2457 if (vm == NULL)
2458 return;
2459
2460 radeon_ring_write(ring, DMA_PACKET(DMA_PACKET_SRBM_WRITE, 0, 0, 0));
2461 radeon_ring_write(ring, (0xf << 16) | ((VM_CONTEXT0_PAGE_TABLE_BASE_ADDR + (vm->id << 2)) >> 2));
2462 radeon_ring_write(ring, vm->pd_gpu_addr >> 12);
2463
2464 /* flush hdp cache */
2465 radeon_ring_write(ring, DMA_PACKET(DMA_PACKET_SRBM_WRITE, 0, 0, 0));
2466 radeon_ring_write(ring, (0xf << 16) | (HDP_MEM_COHERENCY_FLUSH_CNTL >> 2));
2467 radeon_ring_write(ring, 1);
2468
2469 /* bits 0-7 are the VM contexts0-7 */
2470 radeon_ring_write(ring, DMA_PACKET(DMA_PACKET_SRBM_WRITE, 0, 0, 0));
2471 radeon_ring_write(ring, (0xf << 16) | (VM_INVALIDATE_REQUEST >> 2));
2472 radeon_ring_write(ring, 1 << vm->id);
2473}
2474