aboutsummaryrefslogtreecommitdiffstats
path: root/drivers
diff options
context:
space:
mode:
authorDave Airlie <airlied@linux.ie>2009-07-10 14:44:47 -0400
committerDave Airlie <airlied@redhat.com>2009-07-15 03:13:19 -0400
commit2a0f8918fc34713ecaeb900ffb9afa61df4cb08e (patch)
tree672d6e6788cd0f4100b912aa7029fa38c513a23c /drivers
parentad49f501867cba87e1e45e5ebae0b12435d68bf1 (diff)
drm/radeon/kms: fix VRAM sizing like DDX does it.
Doing this like the DDX seems like the most sure fire way to avoid having to reinvent it slowly and painfully. At the moment we keep getting things wrong with aper vs vram, so we know the DDX does it right. booted on PCI r100, PCIE rv370, IGP rs400. Signed-off-by: Dave Airlie <airlied@redhat.com>
Diffstat (limited to 'drivers')
-rw-r--r--drivers/gpu/drm/radeon/r100.c65
-rw-r--r--drivers/gpu/drm/radeon/r300.c4
-rw-r--r--drivers/gpu/drm/radeon/r520.c4
-rw-r--r--drivers/gpu/drm/radeon/radeon.h2
-rw-r--r--drivers/gpu/drm/radeon/radeon_device.c7
-rw-r--r--drivers/gpu/drm/radeon/rs400.c14
-rw-r--r--drivers/gpu/drm/radeon/rv515.c6
7 files changed, 71 insertions, 31 deletions
diff --git a/drivers/gpu/drm/radeon/r100.c b/drivers/gpu/drm/radeon/r100.c
index 154648a2c027..97c9229b9299 100644
--- a/drivers/gpu/drm/radeon/r100.c
+++ b/drivers/gpu/drm/radeon/r100.c
@@ -1360,9 +1360,50 @@ static void r100_vram_get_type(struct radeon_device *rdev)
1360 } 1360 }
1361} 1361}
1362 1362
1363void r100_vram_info(struct radeon_device *rdev) 1363static u32 r100_get_accessible_vram(struct radeon_device *rdev)
1364{ 1364{
1365 r100_vram_get_type(rdev); 1365 u32 aper_size;
1366 u8 byte;
1367
1368 aper_size = RREG32(RADEON_CONFIG_APER_SIZE);
1369
1370 /* Set HDP_APER_CNTL only on cards that are known not to be broken,
1371 * that is has the 2nd generation multifunction PCI interface
1372 */
1373 if (rdev->family == CHIP_RV280 ||
1374 rdev->family >= CHIP_RV350) {
1375 WREG32_P(RADEON_HOST_PATH_CNTL, RADEON_HDP_APER_CNTL,
1376 ~RADEON_HDP_APER_CNTL);
1377 DRM_INFO("Generation 2 PCI interface, using max accessible memory\n");
1378 return aper_size * 2;
1379 }
1380
1381 /* Older cards have all sorts of funny issues to deal with. First
1382 * check if it's a multifunction card by reading the PCI config
1383 * header type... Limit those to one aperture size
1384 */
1385 pci_read_config_byte(rdev->pdev, 0xe, &byte);
1386 if (byte & 0x80) {
1387 DRM_INFO("Generation 1 PCI interface in multifunction mode\n");
1388 DRM_INFO("Limiting VRAM to one aperture\n");
1389 return aper_size;
1390 }
1391
1392 /* Single function older card. We read HDP_APER_CNTL to see how the BIOS
1393 * have set it up. We don't write this as it's broken on some ASICs but
1394 * we expect the BIOS to have done the right thing (might be too optimistic...)
1395 */
1396 if (RREG32(RADEON_HOST_PATH_CNTL) & RADEON_HDP_APER_CNTL)
1397 return aper_size * 2;
1398 return aper_size;
1399}
1400
1401void r100_vram_init_sizes(struct radeon_device *rdev)
1402{
1403 u64 config_aper_size;
1404 u32 accessible;
1405
1406 config_aper_size = RREG32(RADEON_CONFIG_APER_SIZE);
1366 1407
1367 if (rdev->flags & RADEON_IS_IGP) { 1408 if (rdev->flags & RADEON_IS_IGP) {
1368 uint32_t tom; 1409 uint32_t tom;
@@ -1383,10 +1424,30 @@ void r100_vram_info(struct radeon_device *rdev)
1383 } 1424 }
1384 /* let driver place VRAM */ 1425 /* let driver place VRAM */
1385 rdev->mc.vram_location = 0xFFFFFFFFUL; 1426 rdev->mc.vram_location = 0xFFFFFFFFUL;
1427 /* Fix for RN50, M6, M7 with 8/16/32(??) MBs of VRAM -
1428 * Novell bug 204882 + along with lots of ubuntu ones */
1429 if (config_aper_size > rdev->mc.vram_size)
1430 rdev->mc.vram_size = config_aper_size;
1386 } 1431 }
1387 1432
1433 /* work out accessible VRAM */
1434 accessible = r100_get_accessible_vram(rdev);
1435
1388 rdev->mc.aper_base = drm_get_resource_start(rdev->ddev, 0); 1436 rdev->mc.aper_base = drm_get_resource_start(rdev->ddev, 0);
1389 rdev->mc.aper_size = drm_get_resource_len(rdev->ddev, 0); 1437 rdev->mc.aper_size = drm_get_resource_len(rdev->ddev, 0);
1438
1439 if (accessible > rdev->mc.aper_size)
1440 accessible = rdev->mc.aper_size;
1441
1442 if (rdev->mc.vram_size > rdev->mc.aper_size)
1443 rdev->mc.vram_size = rdev->mc.aper_size;
1444}
1445
1446void r100_vram_info(struct radeon_device *rdev)
1447{
1448 r100_vram_get_type(rdev);
1449
1450 r100_vram_init_sizes(rdev);
1390} 1451}
1391 1452
1392 1453
diff --git a/drivers/gpu/drm/radeon/r300.c b/drivers/gpu/drm/radeon/r300.c
index 6435d659cbd1..0e0e094da503 100644
--- a/drivers/gpu/drm/radeon/r300.c
+++ b/drivers/gpu/drm/radeon/r300.c
@@ -585,10 +585,8 @@ void r300_vram_info(struct radeon_device *rdev)
585 } else { 585 } else {
586 rdev->mc.vram_width = 64; 586 rdev->mc.vram_width = 64;
587 } 587 }
588 rdev->mc.vram_size = RREG32(RADEON_CONFIG_MEMSIZE);
589 588
590 rdev->mc.aper_base = drm_get_resource_start(rdev->ddev, 0); 589 r100_vram_init_sizes(rdev);
591 rdev->mc.aper_size = drm_get_resource_len(rdev->ddev, 0);
592} 590}
593 591
594 592
diff --git a/drivers/gpu/drm/radeon/r520.c b/drivers/gpu/drm/radeon/r520.c
index 570a244bd88b..b6bd3758db6b 100644
--- a/drivers/gpu/drm/radeon/r520.c
+++ b/drivers/gpu/drm/radeon/r520.c
@@ -227,8 +227,6 @@ static void r520_vram_get_type(struct radeon_device *rdev)
227void r520_vram_info(struct radeon_device *rdev) 227void r520_vram_info(struct radeon_device *rdev)
228{ 228{
229 r520_vram_get_type(rdev); 229 r520_vram_get_type(rdev);
230 rdev->mc.vram_size = RREG32(RADEON_CONFIG_MEMSIZE);
231 230
232 rdev->mc.aper_base = drm_get_resource_start(rdev->ddev, 0); 231 r100_vram_init_sizes(rdev);
233 rdev->mc.aper_size = drm_get_resource_len(rdev->ddev, 0);
234} 232}
diff --git a/drivers/gpu/drm/radeon/radeon.h b/drivers/gpu/drm/radeon/radeon.h
index 3060ce14071e..248e3341a984 100644
--- a/drivers/gpu/drm/radeon/radeon.h
+++ b/drivers/gpu/drm/radeon/radeon.h
@@ -541,6 +541,8 @@ union radeon_asic_config {
541 struct r300_asic r300; 541 struct r300_asic r300;
542}; 542};
543 543
544/* r100 */
545void r100_vram_init_sizes(struct radeon_device *rdev);
544 546
545/* 547/*
546 * IOCTL. 548 * IOCTL.
diff --git a/drivers/gpu/drm/radeon/radeon_device.c b/drivers/gpu/drm/radeon/radeon_device.c
index 27a5ac969953..cdef6eb01baf 100644
--- a/drivers/gpu/drm/radeon/radeon_device.c
+++ b/drivers/gpu/drm/radeon/radeon_device.c
@@ -561,12 +561,7 @@ int radeon_device_init(struct radeon_device *rdev,
561 } 561 }
562 /* Get vram informations */ 562 /* Get vram informations */
563 radeon_vram_info(rdev); 563 radeon_vram_info(rdev);
564 /* Device is severly broken if aper size > vram size. 564
565 * for RN50/M6/M7 - Novell bug 204882 ?
566 */
567 if (rdev->mc.vram_size < rdev->mc.aper_size) {
568 rdev->mc.vram_size = rdev->mc.aper_size;
569 }
570 /* Add an MTRR for the VRAM */ 565 /* Add an MTRR for the VRAM */
571 rdev->mc.vram_mtrr = mtrr_add(rdev->mc.aper_base, rdev->mc.aper_size, 566 rdev->mc.vram_mtrr = mtrr_add(rdev->mc.aper_base, rdev->mc.aper_size,
572 MTRR_TYPE_WRCOMB, 1); 567 MTRR_TYPE_WRCOMB, 1);
diff --git a/drivers/gpu/drm/radeon/rs400.c b/drivers/gpu/drm/radeon/rs400.c
index a18d053065c0..daf24e85cba3 100644
--- a/drivers/gpu/drm/radeon/rs400.c
+++ b/drivers/gpu/drm/radeon/rs400.c
@@ -292,24 +292,12 @@ void rs400_gpu_init(struct radeon_device *rdev)
292 */ 292 */
293void rs400_vram_info(struct radeon_device *rdev) 293void rs400_vram_info(struct radeon_device *rdev)
294{ 294{
295 uint32_t tom;
296
297 rs400_gart_adjust_size(rdev); 295 rs400_gart_adjust_size(rdev);
298 /* DDR for all card after R300 & IGP */ 296 /* DDR for all card after R300 & IGP */
299 rdev->mc.vram_is_ddr = true; 297 rdev->mc.vram_is_ddr = true;
300 rdev->mc.vram_width = 128; 298 rdev->mc.vram_width = 128;
301 299
302 /* read NB_TOM to get the amount of ram stolen for the GPU */ 300 r100_vram_init_sizes(rdev);
303 tom = RREG32(RADEON_NB_TOM);
304 rdev->mc.vram_size = (((tom >> 16) - (tom & 0xffff) + 1) << 16);
305 WREG32(RADEON_CONFIG_MEMSIZE, rdev->mc.vram_size);
306
307 /* RS480 IGPs don't seem to translate to main RAM, they
308 * just reserve and scan out of it. So setting VRAM location
309 * to say 0, will actually trash the OS. */
310 rdev->mc.vram_location = (tom & 0xffff) << 16;
311 rdev->mc.aper_base = drm_get_resource_start(rdev->ddev, 0);
312 rdev->mc.aper_size = drm_get_resource_len(rdev->ddev, 0);
313} 301}
314 302
315 303
diff --git a/drivers/gpu/drm/radeon/rv515.c b/drivers/gpu/drm/radeon/rv515.c
index d1384d3991ad..677929ed8ed3 100644
--- a/drivers/gpu/drm/radeon/rv515.c
+++ b/drivers/gpu/drm/radeon/rv515.c
@@ -395,10 +395,8 @@ static void rv515_vram_get_type(struct radeon_device *rdev)
395void rv515_vram_info(struct radeon_device *rdev) 395void rv515_vram_info(struct radeon_device *rdev)
396{ 396{
397 rv515_vram_get_type(rdev); 397 rv515_vram_get_type(rdev);
398 rdev->mc.vram_size = RREG32(RADEON_CONFIG_MEMSIZE); 398
399 399 r100_vram_init_sizes(rdev);
400 rdev->mc.aper_base = drm_get_resource_start(rdev->ddev, 0);
401 rdev->mc.aper_size = drm_get_resource_len(rdev->ddev, 0);
402} 400}
403 401
404 402