aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/gpu/drm/radeon/r100.c
diff options
context:
space:
mode:
authorJerome Glisse <jglisse@redhat.com>2009-10-01 04:12:06 -0400
committerDave Airlie <airlied@redhat.com>2009-10-01 18:51:49 -0400
commitd4550907157d8b3d5286157c15f1200c44842269 (patch)
tree0e9733667b3608ca44929650c8431878134c0315 /drivers/gpu/drm/radeon/r100.c
parent207bf9e90cd40f91d4662127b8ae3b64e6b101c4 (diff)
drm/radeon/kms: Convert R100 to new init path (V2)
New init path allow to simply asic initialization and make easier to trace what happen on each different asic. We are removing most callback. More cleanup should happen latter to remove even more callback. Also cleanup register specific to R100,RV200,RV250. Version 2 correct the placement on IGP of the VRAM inside GPU address space to match the stollen RAM placement of IGP. Signed-off-by: Jerome Glisse <jglisse@redhat.com> Signed-off-by: Dave Airlie <airlied@redhat.com>
Diffstat (limited to 'drivers/gpu/drm/radeon/r100.c')
-rw-r--r--drivers/gpu/drm/radeon/r100.c413
1 files changed, 255 insertions, 158 deletions
diff --git a/drivers/gpu/drm/radeon/r100.c b/drivers/gpu/drm/radeon/r100.c
index dc45ec1d4189..0a475617a70f 100644
--- a/drivers/gpu/drm/radeon/r100.c
+++ b/drivers/gpu/drm/radeon/r100.c
@@ -32,6 +32,9 @@
32#include "radeon_reg.h" 32#include "radeon_reg.h"
33#include "radeon.h" 33#include "radeon.h"
34#include "r100d.h" 34#include "r100d.h"
35#include "rs100d.h"
36#include "rv200d.h"
37#include "rv250d.h"
35 38
36#include <linux/firmware.h> 39#include <linux/firmware.h>
37#include <linux/platform_device.h> 40#include <linux/platform_device.h>
@@ -60,18 +63,7 @@ MODULE_FIRMWARE(FIRMWARE_R520);
60 63
61/* This files gather functions specifics to: 64/* This files gather functions specifics to:
62 * r100,rv100,rs100,rv200,rs200,r200,rv250,rs300,rv280 65 * r100,rv100,rs100,rv200,rs200,r200,rv250,rs300,rv280
63 *
64 * Some of these functions might be used by newer ASICs.
65 */ 66 */
66int r200_init(struct radeon_device *rdev);
67void r100_hdp_reset(struct radeon_device *rdev);
68void r100_gpu_init(struct radeon_device *rdev);
69int r100_gui_wait_for_idle(struct radeon_device *rdev);
70int r100_mc_wait_for_idle(struct radeon_device *rdev);
71void r100_gpu_wait_for_vsync(struct radeon_device *rdev);
72void r100_gpu_wait_for_vsync2(struct radeon_device *rdev);
73int r100_debugfs_mc_info_init(struct radeon_device *rdev);
74
75 67
76/* 68/*
77 * PCI GART 69 * PCI GART
@@ -152,136 +144,6 @@ void r100_pci_gart_fini(struct radeon_device *rdev)
152 radeon_gart_fini(rdev); 144 radeon_gart_fini(rdev);
153} 145}
154 146
155
156/*
157 * MC
158 */
159void r100_mc_disable_clients(struct radeon_device *rdev)
160{
161 uint32_t ov0_scale_cntl, crtc_ext_cntl, crtc_gen_cntl, crtc2_gen_cntl;
162
163 /* FIXME: is this function correct for rs100,rs200,rs300 ? */
164 if (r100_gui_wait_for_idle(rdev)) {
165 printk(KERN_WARNING "Failed to wait GUI idle while "
166 "programming pipes. Bad things might happen.\n");
167 }
168
169 /* stop display and memory access */
170 ov0_scale_cntl = RREG32(RADEON_OV0_SCALE_CNTL);
171 WREG32(RADEON_OV0_SCALE_CNTL, ov0_scale_cntl & ~RADEON_SCALER_ENABLE);
172 crtc_ext_cntl = RREG32(RADEON_CRTC_EXT_CNTL);
173 WREG32(RADEON_CRTC_EXT_CNTL, crtc_ext_cntl | RADEON_CRTC_DISPLAY_DIS);
174 crtc_gen_cntl = RREG32(RADEON_CRTC_GEN_CNTL);
175
176 r100_gpu_wait_for_vsync(rdev);
177
178 WREG32(RADEON_CRTC_GEN_CNTL,
179 (crtc_gen_cntl & ~(RADEON_CRTC_CUR_EN | RADEON_CRTC_ICON_EN)) |
180 RADEON_CRTC_DISP_REQ_EN_B | RADEON_CRTC_EXT_DISP_EN);
181
182 if (!(rdev->flags & RADEON_SINGLE_CRTC)) {
183 crtc2_gen_cntl = RREG32(RADEON_CRTC2_GEN_CNTL);
184
185 r100_gpu_wait_for_vsync2(rdev);
186 WREG32(RADEON_CRTC2_GEN_CNTL,
187 (crtc2_gen_cntl &
188 ~(RADEON_CRTC2_CUR_EN | RADEON_CRTC2_ICON_EN)) |
189 RADEON_CRTC2_DISP_REQ_EN_B);
190 }
191
192 udelay(500);
193}
194
195void r100_mc_setup(struct radeon_device *rdev)
196{
197 uint32_t tmp;
198 int r;
199
200 r = r100_debugfs_mc_info_init(rdev);
201 if (r) {
202 DRM_ERROR("Failed to register debugfs file for R100 MC !\n");
203 }
204 /* Write VRAM size in case we are limiting it */
205 WREG32(RADEON_CONFIG_MEMSIZE, rdev->mc.real_vram_size);
206 /* Novell bug 204882 for RN50/M6/M7 with 8/16/32MB VRAM,
207 * if the aperture is 64MB but we have 32MB VRAM
208 * we report only 32MB VRAM but we have to set MC_FB_LOCATION
209 * to 64MB, otherwise the gpu accidentially dies */
210 tmp = rdev->mc.vram_location + rdev->mc.mc_vram_size - 1;
211 tmp = REG_SET(RADEON_MC_FB_TOP, tmp >> 16);
212 tmp |= REG_SET(RADEON_MC_FB_START, rdev->mc.vram_location >> 16);
213 WREG32(RADEON_MC_FB_LOCATION, tmp);
214
215 /* Enable bus mastering */
216 tmp = RREG32(RADEON_BUS_CNTL) & ~RADEON_BUS_MASTER_DIS;
217 WREG32(RADEON_BUS_CNTL, tmp);
218
219 if (rdev->flags & RADEON_IS_AGP) {
220 tmp = rdev->mc.gtt_location + rdev->mc.gtt_size - 1;
221 tmp = REG_SET(RADEON_MC_AGP_TOP, tmp >> 16);
222 tmp |= REG_SET(RADEON_MC_AGP_START, rdev->mc.gtt_location >> 16);
223 WREG32(RADEON_MC_AGP_LOCATION, tmp);
224 WREG32(RADEON_AGP_BASE, rdev->mc.agp_base);
225 } else {
226 WREG32(RADEON_MC_AGP_LOCATION, 0x0FFFFFFF);
227 WREG32(RADEON_AGP_BASE, 0);
228 }
229
230 tmp = RREG32(RADEON_HOST_PATH_CNTL) & RADEON_HDP_APER_CNTL;
231 tmp |= (7 << 28);
232 WREG32(RADEON_HOST_PATH_CNTL, tmp | RADEON_HDP_SOFT_RESET | RADEON_HDP_READ_BUFFER_INVALIDATE);
233 (void)RREG32(RADEON_HOST_PATH_CNTL);
234 WREG32(RADEON_HOST_PATH_CNTL, tmp);
235 (void)RREG32(RADEON_HOST_PATH_CNTL);
236}
237
238int r100_mc_init(struct radeon_device *rdev)
239{
240 int r;
241
242 if (r100_debugfs_rbbm_init(rdev)) {
243 DRM_ERROR("Failed to register debugfs file for RBBM !\n");
244 }
245
246 r100_gpu_init(rdev);
247 /* Disable gart which also disable out of gart access */
248 r100_pci_gart_disable(rdev);
249
250 /* Setup GPU memory space */
251 rdev->mc.gtt_location = 0xFFFFFFFFUL;
252 if (rdev->flags & RADEON_IS_AGP) {
253 r = radeon_agp_init(rdev);
254 if (r) {
255 printk(KERN_WARNING "[drm] Disabling AGP\n");
256 rdev->flags &= ~RADEON_IS_AGP;
257 rdev->mc.gtt_size = radeon_gart_size * 1024 * 1024;
258 } else {
259 rdev->mc.gtt_location = rdev->mc.agp_base;
260 }
261 }
262 r = radeon_mc_setup(rdev);
263 if (r) {
264 return r;
265 }
266
267 r100_mc_disable_clients(rdev);
268 if (r100_mc_wait_for_idle(rdev)) {
269 printk(KERN_WARNING "Failed to wait MC idle while "
270 "programming pipes. Bad things might happen.\n");
271 }
272
273 r100_mc_setup(rdev);
274 return 0;
275}
276
277void r100_mc_fini(struct radeon_device *rdev)
278{
279}
280
281
282/*
283 * Interrupts
284 */
285int r100_irq_set(struct radeon_device *rdev) 147int r100_irq_set(struct radeon_device *rdev)
286{ 148{
287 uint32_t tmp = 0; 149 uint32_t tmp = 0;
@@ -358,10 +220,6 @@ u32 r100_get_vblank_counter(struct radeon_device *rdev, int crtc)
358 return RREG32(RADEON_CRTC2_CRNT_FRAME); 220 return RREG32(RADEON_CRTC2_CRNT_FRAME);
359} 221}
360 222
361
362/*
363 * Fence emission
364 */
365void r100_fence_ring_emit(struct radeon_device *rdev, 223void r100_fence_ring_emit(struct radeon_device *rdev,
366 struct radeon_fence *fence) 224 struct radeon_fence *fence)
367{ 225{
@@ -377,10 +235,6 @@ void r100_fence_ring_emit(struct radeon_device *rdev,
377 radeon_ring_write(rdev, RADEON_SW_INT_FIRE); 235 radeon_ring_write(rdev, RADEON_SW_INT_FIRE);
378} 236}
379 237
380
381/*
382 * Writeback
383 */
384int r100_wb_init(struct radeon_device *rdev) 238int r100_wb_init(struct radeon_device *rdev)
385{ 239{
386 int r; 240 int r;
@@ -504,10 +358,6 @@ int r100_copy_blit(struct radeon_device *rdev,
504 return r; 358 return r;
505} 359}
506 360
507
508/*
509 * CP
510 */
511static int r100_cp_wait_for_idle(struct radeon_device *rdev) 361static int r100_cp_wait_for_idle(struct radeon_device *rdev)
512{ 362{
513 unsigned i; 363 unsigned i;
@@ -612,6 +462,7 @@ static int r100_cp_init_microcode(struct radeon_device *rdev)
612 } 462 }
613 return err; 463 return err;
614} 464}
465
615static void r100_cp_load_microcode(struct radeon_device *rdev) 466static void r100_cp_load_microcode(struct radeon_device *rdev)
616{ 467{
617 const __be32 *fw_data; 468 const __be32 *fw_data;
@@ -1976,7 +1827,7 @@ void r100_pll_wreg(struct radeon_device *rdev, uint32_t reg, uint32_t v)
1976 r100_pll_errata_after_data(rdev); 1827 r100_pll_errata_after_data(rdev);
1977} 1828}
1978 1829
1979int r100_init(struct radeon_device *rdev) 1830void r100_set_safe_registers(struct radeon_device *rdev)
1980{ 1831{
1981 if (ASIC_IS_RN50(rdev)) { 1832 if (ASIC_IS_RN50(rdev)) {
1982 rdev->config.r100.reg_safe_bm = rn50_reg_safe_bm; 1833 rdev->config.r100.reg_safe_bm = rn50_reg_safe_bm;
@@ -1985,9 +1836,8 @@ int r100_init(struct radeon_device *rdev)
1985 rdev->config.r100.reg_safe_bm = r100_reg_safe_bm; 1836 rdev->config.r100.reg_safe_bm = r100_reg_safe_bm;
1986 rdev->config.r100.reg_safe_bm_size = ARRAY_SIZE(r100_reg_safe_bm); 1837 rdev->config.r100.reg_safe_bm_size = ARRAY_SIZE(r100_reg_safe_bm);
1987 } else { 1838 } else {
1988 return r200_init(rdev); 1839 r200_set_safe_registers(rdev);
1989 } 1840 }
1990 return 0;
1991} 1841}
1992 1842
1993/* 1843/*
@@ -3152,8 +3002,255 @@ void r100_mc_resume(struct radeon_device *rdev, struct r100_mc_save *save)
3152 3002
3153void r100_vga_render_disable(struct radeon_device *rdev) 3003void r100_vga_render_disable(struct radeon_device *rdev)
3154{ 3004{
3155 u32 tmp; 3005 u32 tmp;
3156 3006
3157 tmp = RREG8(R_0003C2_GENMO_WT); 3007 tmp = RREG8(R_0003C2_GENMO_WT);
3158 WREG8(R_0003C2_GENMO_WT, C_0003C2_VGA_RAM_EN & tmp); 3008 WREG8(R_0003C2_GENMO_WT, C_0003C2_VGA_RAM_EN & tmp);
3159} 3009}
3010
3011static void r100_debugfs(struct radeon_device *rdev)
3012{
3013 int r;
3014
3015 r = r100_debugfs_mc_info_init(rdev);
3016 if (r)
3017 dev_warn(rdev->dev, "Failed to create r100_mc debugfs file.\n");
3018}
3019
3020static void r100_mc_program(struct radeon_device *rdev)
3021{
3022 struct r100_mc_save save;
3023
3024 /* Stops all mc clients */
3025 r100_mc_stop(rdev, &save);
3026 if (rdev->flags & RADEON_IS_AGP) {
3027 WREG32(R_00014C_MC_AGP_LOCATION,
3028 S_00014C_MC_AGP_START(rdev->mc.gtt_start >> 16) |
3029 S_00014C_MC_AGP_TOP(rdev->mc.gtt_end >> 16));
3030 WREG32(R_000170_AGP_BASE, lower_32_bits(rdev->mc.agp_base));
3031 if (rdev->family > CHIP_RV200)
3032 WREG32(R_00015C_AGP_BASE_2,
3033 upper_32_bits(rdev->mc.agp_base) & 0xff);
3034 } else {
3035 WREG32(R_00014C_MC_AGP_LOCATION, 0x0FFFFFFF);
3036 WREG32(R_000170_AGP_BASE, 0);
3037 if (rdev->family > CHIP_RV200)
3038 WREG32(R_00015C_AGP_BASE_2, 0);
3039 }
3040 /* Wait for mc idle */
3041 if (r100_mc_wait_for_idle(rdev))
3042 dev_warn(rdev->dev, "Wait for MC idle timeout.\n");
3043 /* Program MC, should be a 32bits limited address space */
3044 WREG32(R_000148_MC_FB_LOCATION,
3045 S_000148_MC_FB_START(rdev->mc.vram_start >> 16) |
3046 S_000148_MC_FB_TOP(rdev->mc.vram_end >> 16));
3047 r100_mc_resume(rdev, &save);
3048}
3049
3050void r100_clock_startup(struct radeon_device *rdev)
3051{
3052 u32 tmp;
3053
3054 if (radeon_dynclks != -1 && radeon_dynclks)
3055 radeon_legacy_set_clock_gating(rdev, 1);
3056 /* We need to force on some of the block */
3057 tmp = RREG32_PLL(R_00000D_SCLK_CNTL);
3058 tmp |= S_00000D_FORCE_CP(1) | S_00000D_FORCE_VIP(1);
3059 if ((rdev->family == CHIP_RV250) || (rdev->family == CHIP_RV280))
3060 tmp |= S_00000D_FORCE_DISP1(1) | S_00000D_FORCE_DISP2(1);
3061 WREG32_PLL(R_00000D_SCLK_CNTL, tmp);
3062}
3063
3064static int r100_startup(struct radeon_device *rdev)
3065{
3066 int r;
3067
3068 r100_mc_program(rdev);
3069 /* Resume clock */
3070 r100_clock_startup(rdev);
3071 /* Initialize GPU configuration (# pipes, ...) */
3072 r100_gpu_init(rdev);
3073 /* Initialize GART (initialize after TTM so we can allocate
3074 * memory through TTM but finalize after TTM) */
3075 if (rdev->flags & RADEON_IS_PCI) {
3076 r = r100_pci_gart_enable(rdev);
3077 if (r)
3078 return r;
3079 }
3080 /* Enable IRQ */
3081 rdev->irq.sw_int = true;
3082 r100_irq_set(rdev);
3083 /* 1M ring buffer */
3084 r = r100_cp_init(rdev, 1024 * 1024);
3085 if (r) {
3086 dev_err(rdev->dev, "failled initializing CP (%d).\n", r);
3087 return r;
3088 }
3089 r = r100_wb_init(rdev);
3090 if (r)
3091 dev_err(rdev->dev, "failled initializing WB (%d).\n", r);
3092 r = r100_ib_init(rdev);
3093 if (r) {
3094 dev_err(rdev->dev, "failled initializing IB (%d).\n", r);
3095 return r;
3096 }
3097 return 0;
3098}
3099
3100int r100_resume(struct radeon_device *rdev)
3101{
3102 /* Make sur GART are not working */
3103 if (rdev->flags & RADEON_IS_PCI)
3104 r100_pci_gart_disable(rdev);
3105 /* Resume clock before doing reset */
3106 r100_clock_startup(rdev);
3107 /* Reset gpu before posting otherwise ATOM will enter infinite loop */
3108 if (radeon_gpu_reset(rdev)) {
3109 dev_warn(rdev->dev, "GPU reset failed ! (0xE40=0x%08X, 0x7C0=0x%08X)\n",
3110 RREG32(R_000E40_RBBM_STATUS),
3111 RREG32(R_0007C0_CP_STAT));
3112 }
3113 /* post */
3114 radeon_combios_asic_init(rdev->ddev);
3115 /* Resume clock after posting */
3116 r100_clock_startup(rdev);
3117 return r100_startup(rdev);
3118}
3119
3120int r100_suspend(struct radeon_device *rdev)
3121{
3122 r100_cp_disable(rdev);
3123 r100_wb_disable(rdev);
3124 r100_irq_disable(rdev);
3125 if (rdev->flags & RADEON_IS_PCI)
3126 r100_pci_gart_disable(rdev);
3127 return 0;
3128}
3129
3130void r100_fini(struct radeon_device *rdev)
3131{
3132 r100_suspend(rdev);
3133 r100_cp_fini(rdev);
3134 r100_wb_fini(rdev);
3135 r100_ib_fini(rdev);
3136 radeon_gem_fini(rdev);
3137 if (rdev->flags & RADEON_IS_PCI)
3138 r100_pci_gart_fini(rdev);
3139 radeon_irq_kms_fini(rdev);
3140 radeon_fence_driver_fini(rdev);
3141 radeon_object_fini(rdev);
3142 radeon_atombios_fini(rdev);
3143 kfree(rdev->bios);
3144 rdev->bios = NULL;
3145}
3146
3147int r100_mc_init(struct radeon_device *rdev)
3148{
3149 int r;
3150 u32 tmp;
3151
3152 /* Setup GPU memory space */
3153 rdev->mc.vram_location = 0xFFFFFFFFUL;
3154 rdev->mc.gtt_location = 0xFFFFFFFFUL;
3155 if (rdev->flags & RADEON_IS_IGP) {
3156 tmp = G_00015C_MC_FB_START(RREG32(R_00015C_NB_TOM));
3157 rdev->mc.vram_location = tmp << 16;
3158 }
3159 if (rdev->flags & RADEON_IS_AGP) {
3160 r = radeon_agp_init(rdev);
3161 if (r) {
3162 printk(KERN_WARNING "[drm] Disabling AGP\n");
3163 rdev->flags &= ~RADEON_IS_AGP;
3164 rdev->mc.gtt_size = radeon_gart_size * 1024 * 1024;
3165 } else {
3166 rdev->mc.gtt_location = rdev->mc.agp_base;
3167 }
3168 }
3169 r = radeon_mc_setup(rdev);
3170 if (r)
3171 return r;
3172 return 0;
3173}
3174
3175int r100_init(struct radeon_device *rdev)
3176{
3177 int r;
3178
3179 rdev->new_init_path = true;
3180 /* Register debugfs file specific to this group of asics */
3181 r100_debugfs(rdev);
3182 /* Disable VGA */
3183 r100_vga_render_disable(rdev);
3184 /* Initialize scratch registers */
3185 radeon_scratch_init(rdev);
3186 /* Initialize surface registers */
3187 radeon_surface_init(rdev);
3188 /* TODO: disable VGA need to use VGA request */
3189 /* BIOS*/
3190 if (!radeon_get_bios(rdev)) {
3191 if (ASIC_IS_AVIVO(rdev))
3192 return -EINVAL;
3193 }
3194 if (rdev->is_atom_bios) {
3195 dev_err(rdev->dev, "Expecting combios for RS400/RS480 GPU\n");
3196 return -EINVAL;
3197 } else {
3198 r = radeon_combios_init(rdev);
3199 if (r)
3200 return r;
3201 }
3202 /* Reset gpu before posting otherwise ATOM will enter infinite loop */
3203 if (radeon_gpu_reset(rdev)) {
3204 dev_warn(rdev->dev,
3205 "GPU reset failed ! (0xE40=0x%08X, 0x7C0=0x%08X)\n",
3206 RREG32(R_000E40_RBBM_STATUS),
3207 RREG32(R_0007C0_CP_STAT));
3208 }
3209 /* check if cards are posted or not */
3210 if (!radeon_card_posted(rdev) && rdev->bios) {
3211 DRM_INFO("GPU not posted. posting now...\n");
3212 radeon_combios_asic_init(rdev->ddev);
3213 }
3214 /* Set asic errata */
3215 r100_errata(rdev);
3216 /* Initialize clocks */
3217 radeon_get_clock_info(rdev->ddev);
3218 /* Get vram informations */
3219 r100_vram_info(rdev);
3220 /* Initialize memory controller (also test AGP) */
3221 r = r100_mc_init(rdev);
3222 if (r)
3223 return r;
3224 /* Fence driver */
3225 r = radeon_fence_driver_init(rdev);
3226 if (r)
3227 return r;
3228 r = radeon_irq_kms_init(rdev);
3229 if (r)
3230 return r;
3231 /* Memory manager */
3232 r = radeon_object_init(rdev);
3233 if (r)
3234 return r;
3235 if (rdev->flags & RADEON_IS_PCI) {
3236 r = r100_pci_gart_init(rdev);
3237 if (r)
3238 return r;
3239 }
3240 r100_set_safe_registers(rdev);
3241 rdev->accel_working = true;
3242 r = r100_startup(rdev);
3243 if (r) {
3244 /* Somethings want wront with the accel init stop accel */
3245 dev_err(rdev->dev, "Disabling GPU acceleration\n");
3246 r100_suspend(rdev);
3247 r100_cp_fini(rdev);
3248 r100_wb_fini(rdev);
3249 r100_ib_fini(rdev);
3250 if (rdev->flags & RADEON_IS_PCI)
3251 r100_pci_gart_fini(rdev);
3252 radeon_irq_kms_fini(rdev);
3253 rdev->accel_working = false;
3254 }
3255 return 0;
3256}