/drivers/video/drm/drm_crtc.c |
---|
249,6 → 249,7 |
else |
return "unknown"; |
} |
EXPORT_SYMBOL(drm_get_connector_status_name); |
/** |
* drm_mode_object_get - allocate a new modeset identifier |
/drivers/video/drm/drm_crtc_helper.c |
---|
121,6 → 121,7 |
connector->helper_private; |
int count = 0; |
int mode_flags = 0; |
bool verbose_prune = true; |
DRM_DEBUG_KMS("[CONNECTOR:%d:%s]\n", connector->base.id, |
drm_get_connector_name(connector)); |
136,10 → 137,7 |
if (connector->funcs->force) |
connector->funcs->force(connector); |
} else { |
// dbgprintf("call detect funcs %p ", connector->funcs); |
// dbgprintf("detect %p\n", connector->funcs->detect); |
connector->status = connector->funcs->detect(connector, true); |
// dbgprintf("status %x\n", connector->status); |
} |
/* Re-enable polling in case the global poll config changed. */ |
152,6 → 150,7 |
DRM_DEBUG_KMS("[CONNECTOR:%d:%s] disconnected\n", |
connector->base.id, drm_get_connector_name(connector)); |
drm_mode_connector_update_edid_property(connector, NULL); |
verbose_prune = false; |
goto prune; |
} |
185,7 → 184,7 |
} |
prune: |
drm_mode_prune_invalid(dev, &connector->modes, true); |
drm_mode_prune_invalid(dev, &connector->modes, verbose_prune); |
if (list_empty(&connector->modes)) |
return 0; |
1007,13 → 1006,21 |
continue; |
connector->status = connector->funcs->detect(connector, false); |
DRM_DEBUG_KMS("[CONNECTOR:%d:%s] status updated from %d to %d\n", |
if (old_status != connector->status) { |
const char *old, *new; |
old = drm_get_connector_status_name(old_status); |
new = drm_get_connector_status_name(connector->status); |
DRM_DEBUG_KMS("[CONNECTOR:%d:%s] " |
"status updated from %s to %s\n", |
connector->base.id, |
drm_get_connector_name(connector), |
old_status, connector->status); |
if (old_status != connector->status) |
old, new); |
changed = true; |
} |
} |
mutex_unlock(&dev->mode_config.mutex); |
1085,10 → 1092,11 |
old_status = connector->status; |
connector->status = connector->funcs->detect(connector, false); |
DRM_DEBUG_KMS("[CONNECTOR:%d:%s] status updated from %d to %d\n", |
DRM_DEBUG_KMS("[CONNECTOR:%d:%s] status updated from %s to %s\n", |
connector->base.id, |
drm_get_connector_name(connector), |
old_status, connector->status); |
drm_get_connector_status_name(old_status), |
drm_get_connector_status_name(connector->status)); |
if (old_status != connector->status) |
changed = true; |
} |
/drivers/video/drm/drm_global.c |
---|
31,6 → 31,7 |
#include <linux/mutex.h> |
#include <linux/slab.h> |
#include <linux/module.h> |
#include <linux/bug.h> |
#include <drm/drm_global.h> |
struct drm_global_item { |
/drivers/video/drm/drm_mm.c |
---|
755,34 → 755,36 |
EXPORT_SYMBOL(drm_mm_debug_table); |
#if defined(CONFIG_DEBUG_FS) |
int drm_mm_dump_table(struct seq_file *m, struct drm_mm *mm) |
static unsigned long drm_mm_dump_hole(struct seq_file *m, struct drm_mm_node *entry) |
{ |
struct drm_mm_node *entry; |
unsigned long total_used = 0, total_free = 0, total = 0; |
unsigned long hole_start, hole_end, hole_size; |
hole_start = drm_mm_hole_node_start(&mm->head_node); |
hole_end = drm_mm_hole_node_end(&mm->head_node); |
if (entry->hole_follows) { |
hole_start = drm_mm_hole_node_start(entry); |
hole_end = drm_mm_hole_node_end(entry); |
hole_size = hole_end - hole_start; |
if (hole_size) |
seq_printf(m, "0x%08lx-0x%08lx: 0x%08lx: free\n", |
hole_start, hole_end, hole_size); |
total_free += hole_size; |
return hole_size; |
} |
return 0; |
} |
int drm_mm_dump_table(struct seq_file *m, struct drm_mm *mm) |
{ |
struct drm_mm_node *entry; |
unsigned long total_used = 0, total_free = 0, total = 0; |
total_free += drm_mm_dump_hole(m, &mm->head_node); |
drm_mm_for_each_node(entry, mm) { |
seq_printf(m, "0x%08lx-0x%08lx: 0x%08lx: used\n", |
entry->start, entry->start + entry->size, |
entry->size); |
total_used += entry->size; |
if (entry->hole_follows) { |
hole_start = drm_mm_hole_node_start(entry); |
hole_end = drm_mm_hole_node_end(entry); |
hole_size = hole_end - hole_start; |
seq_printf(m, "0x%08lx-0x%08lx: 0x%08lx: free\n", |
hole_start, hole_end, hole_size); |
total_free += hole_size; |
total_free += drm_mm_dump_hole(m, entry); |
} |
} |
total = total_free + total_used; |
seq_printf(m, "total: %lu, used %lu free %lu\n", total, total_used, total_free); |
/drivers/video/drm/i915/i915_gem_gtt.c |
---|
661,8 → 661,6 |
gtt_size -= I915_PPGTT_PD_ENTRIES*PAGE_SIZE; |
} |
// gtt_size -= LFB_SIZE; |
i915_gem_setup_global_gtt(dev, LFB_SIZE, mappable_size, gtt_size); |
ret = i915_gem_init_aliasing_ppgtt(dev); |
/drivers/video/drm/i915/i915_gem_stolen.c |
---|
312,6 → 312,71 |
return NULL; |
} |
struct drm_i915_gem_object * |
i915_gem_object_create_stolen_for_preallocated(struct drm_device *dev, |
u32 stolen_offset, |
u32 gtt_offset, |
u32 size) |
{ |
struct drm_i915_private *dev_priv = dev->dev_private; |
struct drm_i915_gem_object *obj; |
struct drm_mm_node *stolen; |
if (dev_priv->mm.stolen_base == 0) |
return NULL; |
DRM_DEBUG_KMS("creating preallocated stolen object: stolen_offset=%x, gtt_offset=%x, size=%x\n", |
stolen_offset, gtt_offset, size); |
/* KISS and expect everything to be page-aligned */ |
BUG_ON(stolen_offset & 4095); |
BUG_ON(gtt_offset & 4095); |
BUG_ON(size & 4095); |
if (WARN_ON(size == 0)) |
return NULL; |
stolen = drm_mm_create_block(&dev_priv->mm.stolen, |
stolen_offset, size, |
false); |
if (stolen == NULL) { |
DRM_DEBUG_KMS("failed to allocate stolen space\n"); |
return NULL; |
} |
obj = _i915_gem_object_create_stolen(dev, stolen); |
if (obj == NULL) { |
DRM_DEBUG_KMS("failed to allocate stolen object\n"); |
drm_mm_put_block(stolen); |
return NULL; |
} |
/* To simplify the initialisation sequence between KMS and GTT, |
* we allow construction of the stolen object prior to |
* setting up the GTT space. The actual reservation will occur |
* later. |
*/ |
if (drm_mm_initialized(&dev_priv->mm.gtt_space)) { |
obj->gtt_space = drm_mm_create_block(&dev_priv->mm.gtt_space, |
gtt_offset, size, |
false); |
if (obj->gtt_space == NULL) { |
DRM_DEBUG_KMS("failed to allocate stolen GTT space\n"); |
drm_gem_object_unreference(&obj->base); |
return NULL; |
} |
} else |
obj->gtt_space = I915_GTT_RESERVED; |
obj->gtt_offset = gtt_offset; |
obj->has_global_gtt_mapping = 1; |
list_add_tail(&obj->gtt_list, &dev_priv->mm.bound_list); |
list_add_tail(&obj->mm_list, &dev_priv->mm.inactive_list); |
return obj; |
} |
void |
i915_gem_object_release_stolen(struct drm_i915_gem_object *obj) |
{ |
/drivers/video/drm/i915/main.c |
---|
54,6 → 54,7 |
static char log[256]; |
struct workqueue_struct *system_wq; |
int driver_wq_state; |
int x86_clflush_size; |
unsigned int tsc_khz; |
66,7 → 67,10 |
int err = 0; |
if(action != 1) |
{ |
driver_wq_state = 0; |
return 0; |
}; |
if( GetService("DISPLAY") != 0 ) |
return 0; |
85,7 → 89,7 |
return 0; |
}; |
} |
dbgprintf(" i915 v3.9-rc8\n cmdline: %s\n", cmdline); |
dbgprintf(" i915 v3.10\n cmdline: %s\n", cmdline); |
cpu_detect(); |
// dbgprintf("\ncache line size %d\n", x86_clflush_size); |
106,7 → 110,7 |
dbgprintf("Set DISPLAY handler\n"); |
struct drm_i915_private *dev_priv = main_device->dev_private; |
driver_wq_state = 1; |
run_workqueue(dev_priv->wq); |
return err; |
/drivers/video/drm/radeon/Makefile |
---|
19,7 → 19,7 |
LIBPATH:= $(DRV_TOPDIR)/ddk |
LIBS:= -lddk -lcore |
LIBS:= -lddk -lcore -lgcc |
LDFLAGS = -nostdlib -shared -s -Map atikms.map --image-base 0\ |
--file-alignment 512 --section-alignment 4096 |
42,11 → 42,14 |
NAME_SRC= \ |
pci.c \ |
$(DRM_TOPDIR)/drm_cache.c \ |
$(DRM_TOPDIR)/drm_crtc.c \ |
$(DRM_TOPDIR)/drm_crtc_helper.c \ |
$(DRM_TOPDIR)/drm_dp_helper.c \ |
$(DRM_TOPDIR)/drm_edid.c \ |
$(DRM_TOPDIR)/drm_fb_helper.c \ |
$(DRM_TOPDIR)/drm_gem.c \ |
$(DRM_TOPDIR)/drm_global.c \ |
$(DRM_TOPDIR)/drm_irq.c \ |
$(DRM_TOPDIR)/drm_mm.c \ |
$(DRM_TOPDIR)/drm_modes.c \ |
66,6 → 69,10 |
radeon_clocks.c \ |
atom.c \ |
ni.c \ |
atombios_crtc.c \ |
atombios_dp.c \ |
atombios_encoders.c \ |
atombios_i2c.c \ |
radeon_agp.c \ |
radeon_asic.c \ |
radeon_atombios.c \ |
73,12 → 80,11 |
radeon_bios.c \ |
radeon_combios.c \ |
radeon_connectors.c \ |
atombios_crtc.c \ |
atombios_dp.c \ |
atombios_encoders.c \ |
atombios_i2c.c \ |
radeon_display.c \ |
radeon_encoders.c \ |
radeon_fence.c \ |
radeon_fb.c \ |
radeon_gart.c \ |
radeon_gem.c \ |
radeon_i2c.c \ |
radeon_irq_kms.c \ |
85,13 → 91,11 |
radeon_legacy_crtc.c \ |
radeon_legacy_encoders.c \ |
radeon_legacy_tv.c \ |
radeon_display.c \ |
radeon_gart.c \ |
radeon_object_kos.c \ |
radeon_pm.c \ |
radeon_ring.c \ |
radeon_object_kos.c \ |
radeon_sa.c \ |
radeon_semaphore.c \ |
radeon_pm.c \ |
r100.c \ |
r200.c \ |
r300.c \ |
106,12 → 110,12 |
rs600.c \ |
rs690.c \ |
rv770.c \ |
radeon_fb.c \ |
rdisplay.c \ |
rdisplay_kms.c \ |
cmdline.c \ |
si.c \ |
si_blit_shaders.c \ |
utils.c \ |
fwblob.asm |
FW_BINS= \ |
/drivers/video/drm/radeon/Makefile.lto |
---|
54,8 → 54,6 |
$(DRM_TOPDIR)/drm_stub.c \ |
$(DRM_TOPDIR)/i2c/i2c-core.c \ |
$(DRM_TOPDIR)/i2c/i2c-algo-bit.c \ |
bitmap.c \ |
hmm.c \ |
r700_vs.c \ |
radeon_device.c \ |
evergreen.c \ |
/drivers/video/drm/radeon/atikms.lds |
---|
33,6 → 33,7 |
*(.debug$F) |
*(.drectve) |
*(.edata) |
*(.eh_frame) |
} |
.idata ALIGN(__section_alignment__): |
/drivers/video/drm/radeon/atom.c |
---|
1236,6 → 1236,8 |
static void atom_index_iio(struct atom_context *ctx, int base) |
{ |
ctx->iio = kzalloc(2 * 256, GFP_KERNEL); |
if (!ctx->iio) |
return; |
while (CU8(base) == ATOM_IIO_START) { |
ctx->iio[CU8(base + 1)] = base + 2; |
base += 2; |
1285,6 → 1287,10 |
ctx->cmd_table = CU16(base + ATOM_ROM_CMD_PTR); |
ctx->data_table = CU16(base + ATOM_ROM_DATA_PTR); |
atom_index_iio(ctx, CU16(ctx->data_table + ATOM_DATA_IIO_PTR) + 4); |
if (!ctx->iio) { |
atom_destroy(ctx); |
return NULL; |
} |
str = CSTR(CU16(base + ATOM_ROM_MSG_PTR)); |
while (*str && ((*str == '\n') || (*str == '\r'))) |
1333,7 → 1339,6 |
void atom_destroy(struct atom_context *ctx) |
{ |
if (ctx->iio) |
kfree(ctx->iio); |
kfree(ctx); |
} |
1387,10 → 1392,10 |
firmware_usage = (struct _ATOM_VRAM_USAGE_BY_FIRMWARE *)(ctx->bios + data_offset); |
DRM_DEBUG("atom firmware requested %08x %dkb\n", |
firmware_usage->asFirmwareVramReserveInfo[0].ulStartAddrUsedByFirmware, |
firmware_usage->asFirmwareVramReserveInfo[0].usFirmwareUseInKb); |
le32_to_cpu(firmware_usage->asFirmwareVramReserveInfo[0].ulStartAddrUsedByFirmware), |
le16_to_cpu(firmware_usage->asFirmwareVramReserveInfo[0].usFirmwareUseInKb)); |
usage_bytes = firmware_usage->asFirmwareVramReserveInfo[0].usFirmwareUseInKb * 1024; |
usage_bytes = le16_to_cpu(firmware_usage->asFirmwareVramReserveInfo[0].usFirmwareUseInKb) * 1024; |
} |
ctx->scratch_size_bytes = 0; |
if (usage_bytes == 0) |
/drivers/video/drm/radeon/atombios.h |
---|
458,6 → 458,7 |
union |
{ |
ATOM_COMPUTE_CLOCK_FREQ ulClock; //Input Parameter |
ULONG ulClockParams; //ULONG access for BE |
ATOM_S_MPLL_FB_DIVIDER ulFbDiv; //Output Parameter |
}; |
UCHAR ucRefDiv; //Output Parameter |
490,6 → 491,7 |
union |
{ |
ATOM_COMPUTE_CLOCK_FREQ ulClock; //Input Parameter |
ULONG ulClockParams; //ULONG access for BE |
ATOM_S_MPLL_FB_DIVIDER ulFbDiv; //Output Parameter |
}; |
UCHAR ucRefDiv; //Output Parameter |
/drivers/video/drm/radeon/atombios_crtc.c |
---|
252,8 → 252,6 |
radeon_crtc->enabled = true; |
/* adjust pm to dpms changes BEFORE enabling crtcs */ |
radeon_pm_compute_clocks(rdev); |
if (ASIC_IS_DCE6(rdev) && !radeon_crtc->in_mode_set) |
atombios_powergate_crtc(crtc, ATOM_DISABLE); |
atombios_enable_crtc(crtc, ATOM_ENABLE); |
if (ASIC_IS_DCE3(rdev) && !ASIC_IS_DCE6(rdev)) |
atombios_enable_crtc_memreq(crtc, ATOM_ENABLE); |
271,8 → 269,6 |
atombios_enable_crtc_memreq(crtc, ATOM_DISABLE); |
atombios_enable_crtc(crtc, ATOM_DISABLE); |
radeon_crtc->enabled = false; |
if (ASIC_IS_DCE6(rdev) && !radeon_crtc->in_mode_set) |
atombios_powergate_crtc(crtc, ATOM_ENABLE); |
/* adjust pm to dpms changes AFTER disabling crtcs */ |
radeon_pm_compute_clocks(rdev); |
break; |
561,6 → 557,9 |
/* use frac fb div on APUs */ |
if (ASIC_IS_DCE41(rdev) || ASIC_IS_DCE61(rdev)) |
radeon_crtc->pll_flags |= RADEON_PLL_USE_FRAC_FB_DIV; |
/* use frac fb div on RS780/RS880 */ |
if ((rdev->family == CHIP_RS780) || (rdev->family == CHIP_RS880)) |
radeon_crtc->pll_flags |= RADEON_PLL_USE_FRAC_FB_DIV; |
if (ASIC_IS_DCE32(rdev) && mode->clock > 165000) |
radeon_crtc->pll_flags |= RADEON_PLL_USE_FRAC_FB_DIV; |
} else { |
1812,12 → 1811,9 |
static void atombios_crtc_prepare(struct drm_crtc *crtc) |
{ |
struct radeon_crtc *radeon_crtc = to_radeon_crtc(crtc); |
struct drm_device *dev = crtc->dev; |
struct radeon_device *rdev = dev->dev_private; |
radeon_crtc->in_mode_set = true; |
/* disable crtc pair power gating before programming */ |
if (ASIC_IS_DCE6(rdev)) |
atombios_powergate_crtc(crtc, ATOM_DISABLE); |
1828,11 → 1824,8 |
static void atombios_crtc_commit(struct drm_crtc *crtc) |
{ |
struct radeon_crtc *radeon_crtc = to_radeon_crtc(crtc); |
atombios_crtc_dpms(crtc, DRM_MODE_DPMS_ON); |
atombios_lock_crtc(crtc, ATOM_DISABLE); |
radeon_crtc->in_mode_set = false; |
} |
static void atombios_crtc_disable(struct drm_crtc *crtc) |
1844,6 → 1837,8 |
int i; |
atombios_crtc_dpms(crtc, DRM_MODE_DPMS_OFF); |
if (ASIC_IS_DCE6(rdev)) |
atombios_powergate_crtc(crtc, ATOM_ENABLE); |
for (i = 0; i < rdev->num_crtc; i++) { |
if (rdev->mode_info.crtcs[i] && |
/drivers/video/drm/radeon/atombios_dp.c |
---|
450,8 → 450,6 |
u8 msg[DP_DPCD_SIZE]; |
int ret, i; |
ENTER(); |
ret = radeon_dp_aux_native_read(radeon_connector, DP_DPCD_REV, msg, |
DP_DPCD_SIZE, 0); |
if (ret > 0) { |
462,10 → 460,9 |
DRM_DEBUG_KMS("\n"); |
radeon_dp_probe_oui(radeon_connector); |
LEAVE(); |
return true; |
} |
FAIL(); |
dig_connector->dpcd[0] = 0; |
return false; |
} |
/drivers/video/drm/radeon/atombios_encoders.c |
---|
667,6 → 667,8 |
int |
atombios_get_encoder_mode(struct drm_encoder *encoder) |
{ |
struct drm_device *dev = encoder->dev; |
struct radeon_device *rdev = dev->dev_private; |
struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder); |
struct drm_connector *connector; |
struct radeon_connector *radeon_connector; |
693,7 → 695,8 |
case DRM_MODE_CONNECTOR_DVII: |
case DRM_MODE_CONNECTOR_HDMIB: /* HDMI-B is basically DL-DVI; analog works fine */ |
if (drm_detect_hdmi_monitor(radeon_connector->edid) && |
radeon_audio) |
radeon_audio && |
!ASIC_IS_DCE6(rdev)) /* remove once we support DCE6 */ |
return ATOM_ENCODER_MODE_HDMI; |
else if (radeon_connector->use_digital) |
return ATOM_ENCODER_MODE_DVI; |
704,7 → 707,8 |
case DRM_MODE_CONNECTOR_HDMIA: |
default: |
if (drm_detect_hdmi_monitor(radeon_connector->edid) && |
radeon_audio) |
radeon_audio && |
!ASIC_IS_DCE6(rdev)) /* remove once we support DCE6 */ |
return ATOM_ENCODER_MODE_HDMI; |
else |
return ATOM_ENCODER_MODE_DVI; |
718,7 → 722,8 |
(dig_connector->dp_sink_type == CONNECTOR_OBJECT_ID_eDP)) |
return ATOM_ENCODER_MODE_DP; |
else if (drm_detect_hdmi_monitor(radeon_connector->edid) && |
radeon_audio) |
radeon_audio && |
!ASIC_IS_DCE6(rdev)) /* remove once we support DCE6 */ |
return ATOM_ENCODER_MODE_HDMI; |
else |
return ATOM_ENCODER_MODE_DVI; |
2150,13 → 2155,10 |
atombios_apply_encoder_quirks(encoder, adjusted_mode); |
if (atombios_get_encoder_mode(encoder) == ATOM_ENCODER_MODE_HDMI) { |
r600_hdmi_enable(encoder); |
if (ASIC_IS_DCE6(rdev)) |
; /* TODO (use pointers instead of if-s?) */ |
else if (ASIC_IS_DCE4(rdev)) |
evergreen_hdmi_setmode(encoder, adjusted_mode); |
else |
r600_hdmi_setmode(encoder, adjusted_mode); |
if (rdev->asic->display.hdmi_enable) |
radeon_hdmi_enable(rdev, encoder, true); |
if (rdev->asic->display.hdmi_setmode) |
radeon_hdmi_setmode(rdev, encoder, adjusted_mode); |
} |
} |
2413,8 → 2415,10 |
disable_done: |
if (radeon_encoder_is_digital(encoder)) { |
if (atombios_get_encoder_mode(encoder) == ATOM_ENCODER_MODE_HDMI) |
r600_hdmi_disable(encoder); |
if (atombios_get_encoder_mode(encoder) == ATOM_ENCODER_MODE_HDMI) { |
if (rdev->asic->display.hdmi_enable) |
radeon_hdmi_enable(rdev, encoder, false); |
} |
dig = radeon_encoder->enc_priv; |
dig->dig_encoder = -1; |
} |
/drivers/video/drm/radeon/bitmap.c |
---|
5,9 → 5,10 |
#include "hmm.h" |
#include "bitmap.h" |
//#define DRIVER_CAPS_0 HW_BIT_BLIT |
#define DRIVER_CAPS_0 0 |
#define DRIVER_CAPS_0 HW_BIT_BLIT |
//#define DRIVER_CAPS_0 0 |
#define DRIVER_CAPS_1 0 |
struct context *context_map[256]; |
16,6 → 17,7 |
extern struct drm_device *main_drm_device; |
#if 0 |
void __attribute__((regparm(1))) destroy_bitmap(bitmap_t *bitmap) |
{ |
44,7 → 46,6 |
__DestroyObject(bitmap); |
}; |
#if 0 |
static int bitmap_get_pages_gtt(struct drm_i915_gem_object *obj) |
{ |
int page_count; |
110,7 → 111,6 |
u32 format; // reserved mbz |
}; |
#endif |
int create_surface(struct drm_device *dev, struct io_call_10 *pbitmap) |
{ |
183,9 → 183,11 |
if (unlikely(ret != 0)) |
goto err3; |
#ifndef __TTM__ |
ret = radeon_bo_user_map(obj, (void**)&uaddr); |
if (unlikely(ret != 0)) |
goto err3; |
#endif |
bitmap->page_count = size/PAGE_SIZE; |
bitmap->max_count = max_size/PAGE_SIZE; |
482,4 → 484,5 |
return NULL; |
}; |
#endif |
/drivers/video/drm/radeon/evergreen.c |
---|
53,6 → 53,864 |
extern void cayman_cp_int_cntl_setup(struct radeon_device *rdev, |
int ring, u32 cp_int_cntl); |
static const u32 evergreen_golden_registers[] = |
{ |
0x3f90, 0xffff0000, 0xff000000, |
0x9148, 0xffff0000, 0xff000000, |
0x3f94, 0xffff0000, 0xff000000, |
0x914c, 0xffff0000, 0xff000000, |
0x9b7c, 0xffffffff, 0x00000000, |
0x8a14, 0xffffffff, 0x00000007, |
0x8b10, 0xffffffff, 0x00000000, |
0x960c, 0xffffffff, 0x54763210, |
0x88c4, 0xffffffff, 0x000000c2, |
0x88d4, 0xffffffff, 0x00000010, |
0x8974, 0xffffffff, 0x00000000, |
0xc78, 0x00000080, 0x00000080, |
0x5eb4, 0xffffffff, 0x00000002, |
0x5e78, 0xffffffff, 0x001000f0, |
0x6104, 0x01000300, 0x00000000, |
0x5bc0, 0x00300000, 0x00000000, |
0x7030, 0xffffffff, 0x00000011, |
0x7c30, 0xffffffff, 0x00000011, |
0x10830, 0xffffffff, 0x00000011, |
0x11430, 0xffffffff, 0x00000011, |
0x12030, 0xffffffff, 0x00000011, |
0x12c30, 0xffffffff, 0x00000011, |
0xd02c, 0xffffffff, 0x08421000, |
0x240c, 0xffffffff, 0x00000380, |
0x8b24, 0xffffffff, 0x00ff0fff, |
0x28a4c, 0x06000000, 0x06000000, |
0x10c, 0x00000001, 0x00000001, |
0x8d00, 0xffffffff, 0x100e4848, |
0x8d04, 0xffffffff, 0x00164745, |
0x8c00, 0xffffffff, 0xe4000003, |
0x8c04, 0xffffffff, 0x40600060, |
0x8c08, 0xffffffff, 0x001c001c, |
0x8cf0, 0xffffffff, 0x08e00620, |
0x8c20, 0xffffffff, 0x00800080, |
0x8c24, 0xffffffff, 0x00800080, |
0x8c18, 0xffffffff, 0x20202078, |
0x8c1c, 0xffffffff, 0x00001010, |
0x28350, 0xffffffff, 0x00000000, |
0xa008, 0xffffffff, 0x00010000, |
0x5cc, 0xffffffff, 0x00000001, |
0x9508, 0xffffffff, 0x00000002, |
0x913c, 0x0000000f, 0x0000000a |
}; |
static const u32 evergreen_golden_registers2[] = |
{ |
0x2f4c, 0xffffffff, 0x00000000, |
0x54f4, 0xffffffff, 0x00000000, |
0x54f0, 0xffffffff, 0x00000000, |
0x5498, 0xffffffff, 0x00000000, |
0x549c, 0xffffffff, 0x00000000, |
0x5494, 0xffffffff, 0x00000000, |
0x53cc, 0xffffffff, 0x00000000, |
0x53c8, 0xffffffff, 0x00000000, |
0x53c4, 0xffffffff, 0x00000000, |
0x53c0, 0xffffffff, 0x00000000, |
0x53bc, 0xffffffff, 0x00000000, |
0x53b8, 0xffffffff, 0x00000000, |
0x53b4, 0xffffffff, 0x00000000, |
0x53b0, 0xffffffff, 0x00000000 |
}; |
static const u32 cypress_mgcg_init[] = |
{ |
0x802c, 0xffffffff, 0xc0000000, |
0x5448, 0xffffffff, 0x00000100, |
0x55e4, 0xffffffff, 0x00000100, |
0x160c, 0xffffffff, 0x00000100, |
0x5644, 0xffffffff, 0x00000100, |
0xc164, 0xffffffff, 0x00000100, |
0x8a18, 0xffffffff, 0x00000100, |
0x897c, 0xffffffff, 0x06000100, |
0x8b28, 0xffffffff, 0x00000100, |
0x9144, 0xffffffff, 0x00000100, |
0x9a60, 0xffffffff, 0x00000100, |
0x9868, 0xffffffff, 0x00000100, |
0x8d58, 0xffffffff, 0x00000100, |
0x9510, 0xffffffff, 0x00000100, |
0x949c, 0xffffffff, 0x00000100, |
0x9654, 0xffffffff, 0x00000100, |
0x9030, 0xffffffff, 0x00000100, |
0x9034, 0xffffffff, 0x00000100, |
0x9038, 0xffffffff, 0x00000100, |
0x903c, 0xffffffff, 0x00000100, |
0x9040, 0xffffffff, 0x00000100, |
0xa200, 0xffffffff, 0x00000100, |
0xa204, 0xffffffff, 0x00000100, |
0xa208, 0xffffffff, 0x00000100, |
0xa20c, 0xffffffff, 0x00000100, |
0x971c, 0xffffffff, 0x00000100, |
0x977c, 0xffffffff, 0x00000100, |
0x3f80, 0xffffffff, 0x00000100, |
0xa210, 0xffffffff, 0x00000100, |
0xa214, 0xffffffff, 0x00000100, |
0x4d8, 0xffffffff, 0x00000100, |
0x9784, 0xffffffff, 0x00000100, |
0x9698, 0xffffffff, 0x00000100, |
0x4d4, 0xffffffff, 0x00000200, |
0x30cc, 0xffffffff, 0x00000100, |
0xd0c0, 0xffffffff, 0xff000100, |
0x802c, 0xffffffff, 0x40000000, |
0x915c, 0xffffffff, 0x00010000, |
0x9160, 0xffffffff, 0x00030002, |
0x9178, 0xffffffff, 0x00070000, |
0x917c, 0xffffffff, 0x00030002, |
0x9180, 0xffffffff, 0x00050004, |
0x918c, 0xffffffff, 0x00010006, |
0x9190, 0xffffffff, 0x00090008, |
0x9194, 0xffffffff, 0x00070000, |
0x9198, 0xffffffff, 0x00030002, |
0x919c, 0xffffffff, 0x00050004, |
0x91a8, 0xffffffff, 0x00010006, |
0x91ac, 0xffffffff, 0x00090008, |
0x91b0, 0xffffffff, 0x00070000, |
0x91b4, 0xffffffff, 0x00030002, |
0x91b8, 0xffffffff, 0x00050004, |
0x91c4, 0xffffffff, 0x00010006, |
0x91c8, 0xffffffff, 0x00090008, |
0x91cc, 0xffffffff, 0x00070000, |
0x91d0, 0xffffffff, 0x00030002, |
0x91d4, 0xffffffff, 0x00050004, |
0x91e0, 0xffffffff, 0x00010006, |
0x91e4, 0xffffffff, 0x00090008, |
0x91e8, 0xffffffff, 0x00000000, |
0x91ec, 0xffffffff, 0x00070000, |
0x91f0, 0xffffffff, 0x00030002, |
0x91f4, 0xffffffff, 0x00050004, |
0x9200, 0xffffffff, 0x00010006, |
0x9204, 0xffffffff, 0x00090008, |
0x9208, 0xffffffff, 0x00070000, |
0x920c, 0xffffffff, 0x00030002, |
0x9210, 0xffffffff, 0x00050004, |
0x921c, 0xffffffff, 0x00010006, |
0x9220, 0xffffffff, 0x00090008, |
0x9224, 0xffffffff, 0x00070000, |
0x9228, 0xffffffff, 0x00030002, |
0x922c, 0xffffffff, 0x00050004, |
0x9238, 0xffffffff, 0x00010006, |
0x923c, 0xffffffff, 0x00090008, |
0x9240, 0xffffffff, 0x00070000, |
0x9244, 0xffffffff, 0x00030002, |
0x9248, 0xffffffff, 0x00050004, |
0x9254, 0xffffffff, 0x00010006, |
0x9258, 0xffffffff, 0x00090008, |
0x925c, 0xffffffff, 0x00070000, |
0x9260, 0xffffffff, 0x00030002, |
0x9264, 0xffffffff, 0x00050004, |
0x9270, 0xffffffff, 0x00010006, |
0x9274, 0xffffffff, 0x00090008, |
0x9278, 0xffffffff, 0x00070000, |
0x927c, 0xffffffff, 0x00030002, |
0x9280, 0xffffffff, 0x00050004, |
0x928c, 0xffffffff, 0x00010006, |
0x9290, 0xffffffff, 0x00090008, |
0x9294, 0xffffffff, 0x00000000, |
0x929c, 0xffffffff, 0x00000001, |
0x802c, 0xffffffff, 0x40010000, |
0x915c, 0xffffffff, 0x00010000, |
0x9160, 0xffffffff, 0x00030002, |
0x9178, 0xffffffff, 0x00070000, |
0x917c, 0xffffffff, 0x00030002, |
0x9180, 0xffffffff, 0x00050004, |
0x918c, 0xffffffff, 0x00010006, |
0x9190, 0xffffffff, 0x00090008, |
0x9194, 0xffffffff, 0x00070000, |
0x9198, 0xffffffff, 0x00030002, |
0x919c, 0xffffffff, 0x00050004, |
0x91a8, 0xffffffff, 0x00010006, |
0x91ac, 0xffffffff, 0x00090008, |
0x91b0, 0xffffffff, 0x00070000, |
0x91b4, 0xffffffff, 0x00030002, |
0x91b8, 0xffffffff, 0x00050004, |
0x91c4, 0xffffffff, 0x00010006, |
0x91c8, 0xffffffff, 0x00090008, |
0x91cc, 0xffffffff, 0x00070000, |
0x91d0, 0xffffffff, 0x00030002, |
0x91d4, 0xffffffff, 0x00050004, |
0x91e0, 0xffffffff, 0x00010006, |
0x91e4, 0xffffffff, 0x00090008, |
0x91e8, 0xffffffff, 0x00000000, |
0x91ec, 0xffffffff, 0x00070000, |
0x91f0, 0xffffffff, 0x00030002, |
0x91f4, 0xffffffff, 0x00050004, |
0x9200, 0xffffffff, 0x00010006, |
0x9204, 0xffffffff, 0x00090008, |
0x9208, 0xffffffff, 0x00070000, |
0x920c, 0xffffffff, 0x00030002, |
0x9210, 0xffffffff, 0x00050004, |
0x921c, 0xffffffff, 0x00010006, |
0x9220, 0xffffffff, 0x00090008, |
0x9224, 0xffffffff, 0x00070000, |
0x9228, 0xffffffff, 0x00030002, |
0x922c, 0xffffffff, 0x00050004, |
0x9238, 0xffffffff, 0x00010006, |
0x923c, 0xffffffff, 0x00090008, |
0x9240, 0xffffffff, 0x00070000, |
0x9244, 0xffffffff, 0x00030002, |
0x9248, 0xffffffff, 0x00050004, |
0x9254, 0xffffffff, 0x00010006, |
0x9258, 0xffffffff, 0x00090008, |
0x925c, 0xffffffff, 0x00070000, |
0x9260, 0xffffffff, 0x00030002, |
0x9264, 0xffffffff, 0x00050004, |
0x9270, 0xffffffff, 0x00010006, |
0x9274, 0xffffffff, 0x00090008, |
0x9278, 0xffffffff, 0x00070000, |
0x927c, 0xffffffff, 0x00030002, |
0x9280, 0xffffffff, 0x00050004, |
0x928c, 0xffffffff, 0x00010006, |
0x9290, 0xffffffff, 0x00090008, |
0x9294, 0xffffffff, 0x00000000, |
0x929c, 0xffffffff, 0x00000001, |
0x802c, 0xffffffff, 0xc0000000 |
}; |
static const u32 redwood_mgcg_init[] = |
{ |
0x802c, 0xffffffff, 0xc0000000, |
0x5448, 0xffffffff, 0x00000100, |
0x55e4, 0xffffffff, 0x00000100, |
0x160c, 0xffffffff, 0x00000100, |
0x5644, 0xffffffff, 0x00000100, |
0xc164, 0xffffffff, 0x00000100, |
0x8a18, 0xffffffff, 0x00000100, |
0x897c, 0xffffffff, 0x06000100, |
0x8b28, 0xffffffff, 0x00000100, |
0x9144, 0xffffffff, 0x00000100, |
0x9a60, 0xffffffff, 0x00000100, |
0x9868, 0xffffffff, 0x00000100, |
0x8d58, 0xffffffff, 0x00000100, |
0x9510, 0xffffffff, 0x00000100, |
0x949c, 0xffffffff, 0x00000100, |
0x9654, 0xffffffff, 0x00000100, |
0x9030, 0xffffffff, 0x00000100, |
0x9034, 0xffffffff, 0x00000100, |
0x9038, 0xffffffff, 0x00000100, |
0x903c, 0xffffffff, 0x00000100, |
0x9040, 0xffffffff, 0x00000100, |
0xa200, 0xffffffff, 0x00000100, |
0xa204, 0xffffffff, 0x00000100, |
0xa208, 0xffffffff, 0x00000100, |
0xa20c, 0xffffffff, 0x00000100, |
0x971c, 0xffffffff, 0x00000100, |
0x977c, 0xffffffff, 0x00000100, |
0x3f80, 0xffffffff, 0x00000100, |
0xa210, 0xffffffff, 0x00000100, |
0xa214, 0xffffffff, 0x00000100, |
0x4d8, 0xffffffff, 0x00000100, |
0x9784, 0xffffffff, 0x00000100, |
0x9698, 0xffffffff, 0x00000100, |
0x4d4, 0xffffffff, 0x00000200, |
0x30cc, 0xffffffff, 0x00000100, |
0xd0c0, 0xffffffff, 0xff000100, |
0x802c, 0xffffffff, 0x40000000, |
0x915c, 0xffffffff, 0x00010000, |
0x9160, 0xffffffff, 0x00030002, |
0x9178, 0xffffffff, 0x00070000, |
0x917c, 0xffffffff, 0x00030002, |
0x9180, 0xffffffff, 0x00050004, |
0x918c, 0xffffffff, 0x00010006, |
0x9190, 0xffffffff, 0x00090008, |
0x9194, 0xffffffff, 0x00070000, |
0x9198, 0xffffffff, 0x00030002, |
0x919c, 0xffffffff, 0x00050004, |
0x91a8, 0xffffffff, 0x00010006, |
0x91ac, 0xffffffff, 0x00090008, |
0x91b0, 0xffffffff, 0x00070000, |
0x91b4, 0xffffffff, 0x00030002, |
0x91b8, 0xffffffff, 0x00050004, |
0x91c4, 0xffffffff, 0x00010006, |
0x91c8, 0xffffffff, 0x00090008, |
0x91cc, 0xffffffff, 0x00070000, |
0x91d0, 0xffffffff, 0x00030002, |
0x91d4, 0xffffffff, 0x00050004, |
0x91e0, 0xffffffff, 0x00010006, |
0x91e4, 0xffffffff, 0x00090008, |
0x91e8, 0xffffffff, 0x00000000, |
0x91ec, 0xffffffff, 0x00070000, |
0x91f0, 0xffffffff, 0x00030002, |
0x91f4, 0xffffffff, 0x00050004, |
0x9200, 0xffffffff, 0x00010006, |
0x9204, 0xffffffff, 0x00090008, |
0x9294, 0xffffffff, 0x00000000, |
0x929c, 0xffffffff, 0x00000001, |
0x802c, 0xffffffff, 0xc0000000 |
}; |
static const u32 cedar_golden_registers[] = |
{ |
0x3f90, 0xffff0000, 0xff000000, |
0x9148, 0xffff0000, 0xff000000, |
0x3f94, 0xffff0000, 0xff000000, |
0x914c, 0xffff0000, 0xff000000, |
0x9b7c, 0xffffffff, 0x00000000, |
0x8a14, 0xffffffff, 0x00000007, |
0x8b10, 0xffffffff, 0x00000000, |
0x960c, 0xffffffff, 0x54763210, |
0x88c4, 0xffffffff, 0x000000c2, |
0x88d4, 0xffffffff, 0x00000000, |
0x8974, 0xffffffff, 0x00000000, |
0xc78, 0x00000080, 0x00000080, |
0x5eb4, 0xffffffff, 0x00000002, |
0x5e78, 0xffffffff, 0x001000f0, |
0x6104, 0x01000300, 0x00000000, |
0x5bc0, 0x00300000, 0x00000000, |
0x7030, 0xffffffff, 0x00000011, |
0x7c30, 0xffffffff, 0x00000011, |
0x10830, 0xffffffff, 0x00000011, |
0x11430, 0xffffffff, 0x00000011, |
0xd02c, 0xffffffff, 0x08421000, |
0x240c, 0xffffffff, 0x00000380, |
0x8b24, 0xffffffff, 0x00ff0fff, |
0x28a4c, 0x06000000, 0x06000000, |
0x10c, 0x00000001, 0x00000001, |
0x8d00, 0xffffffff, 0x100e4848, |
0x8d04, 0xffffffff, 0x00164745, |
0x8c00, 0xffffffff, 0xe4000003, |
0x8c04, 0xffffffff, 0x40600060, |
0x8c08, 0xffffffff, 0x001c001c, |
0x8cf0, 0xffffffff, 0x08e00410, |
0x8c20, 0xffffffff, 0x00800080, |
0x8c24, 0xffffffff, 0x00800080, |
0x8c18, 0xffffffff, 0x20202078, |
0x8c1c, 0xffffffff, 0x00001010, |
0x28350, 0xffffffff, 0x00000000, |
0xa008, 0xffffffff, 0x00010000, |
0x5cc, 0xffffffff, 0x00000001, |
0x9508, 0xffffffff, 0x00000002 |
}; |
static const u32 cedar_mgcg_init[] = |
{ |
0x802c, 0xffffffff, 0xc0000000, |
0x5448, 0xffffffff, 0x00000100, |
0x55e4, 0xffffffff, 0x00000100, |
0x160c, 0xffffffff, 0x00000100, |
0x5644, 0xffffffff, 0x00000100, |
0xc164, 0xffffffff, 0x00000100, |
0x8a18, 0xffffffff, 0x00000100, |
0x897c, 0xffffffff, 0x06000100, |
0x8b28, 0xffffffff, 0x00000100, |
0x9144, 0xffffffff, 0x00000100, |
0x9a60, 0xffffffff, 0x00000100, |
0x9868, 0xffffffff, 0x00000100, |
0x8d58, 0xffffffff, 0x00000100, |
0x9510, 0xffffffff, 0x00000100, |
0x949c, 0xffffffff, 0x00000100, |
0x9654, 0xffffffff, 0x00000100, |
0x9030, 0xffffffff, 0x00000100, |
0x9034, 0xffffffff, 0x00000100, |
0x9038, 0xffffffff, 0x00000100, |
0x903c, 0xffffffff, 0x00000100, |
0x9040, 0xffffffff, 0x00000100, |
0xa200, 0xffffffff, 0x00000100, |
0xa204, 0xffffffff, 0x00000100, |
0xa208, 0xffffffff, 0x00000100, |
0xa20c, 0xffffffff, 0x00000100, |
0x971c, 0xffffffff, 0x00000100, |
0x977c, 0xffffffff, 0x00000100, |
0x3f80, 0xffffffff, 0x00000100, |
0xa210, 0xffffffff, 0x00000100, |
0xa214, 0xffffffff, 0x00000100, |
0x4d8, 0xffffffff, 0x00000100, |
0x9784, 0xffffffff, 0x00000100, |
0x9698, 0xffffffff, 0x00000100, |
0x4d4, 0xffffffff, 0x00000200, |
0x30cc, 0xffffffff, 0x00000100, |
0xd0c0, 0xffffffff, 0xff000100, |
0x802c, 0xffffffff, 0x40000000, |
0x915c, 0xffffffff, 0x00010000, |
0x9178, 0xffffffff, 0x00050000, |
0x917c, 0xffffffff, 0x00030002, |
0x918c, 0xffffffff, 0x00010004, |
0x9190, 0xffffffff, 0x00070006, |
0x9194, 0xffffffff, 0x00050000, |
0x9198, 0xffffffff, 0x00030002, |
0x91a8, 0xffffffff, 0x00010004, |
0x91ac, 0xffffffff, 0x00070006, |
0x91e8, 0xffffffff, 0x00000000, |
0x9294, 0xffffffff, 0x00000000, |
0x929c, 0xffffffff, 0x00000001, |
0x802c, 0xffffffff, 0xc0000000 |
}; |
static const u32 juniper_mgcg_init[] = |
{ |
0x802c, 0xffffffff, 0xc0000000, |
0x5448, 0xffffffff, 0x00000100, |
0x55e4, 0xffffffff, 0x00000100, |
0x160c, 0xffffffff, 0x00000100, |
0x5644, 0xffffffff, 0x00000100, |
0xc164, 0xffffffff, 0x00000100, |
0x8a18, 0xffffffff, 0x00000100, |
0x897c, 0xffffffff, 0x06000100, |
0x8b28, 0xffffffff, 0x00000100, |
0x9144, 0xffffffff, 0x00000100, |
0x9a60, 0xffffffff, 0x00000100, |
0x9868, 0xffffffff, 0x00000100, |
0x8d58, 0xffffffff, 0x00000100, |
0x9510, 0xffffffff, 0x00000100, |
0x949c, 0xffffffff, 0x00000100, |
0x9654, 0xffffffff, 0x00000100, |
0x9030, 0xffffffff, 0x00000100, |
0x9034, 0xffffffff, 0x00000100, |
0x9038, 0xffffffff, 0x00000100, |
0x903c, 0xffffffff, 0x00000100, |
0x9040, 0xffffffff, 0x00000100, |
0xa200, 0xffffffff, 0x00000100, |
0xa204, 0xffffffff, 0x00000100, |
0xa208, 0xffffffff, 0x00000100, |
0xa20c, 0xffffffff, 0x00000100, |
0x971c, 0xffffffff, 0x00000100, |
0xd0c0, 0xffffffff, 0xff000100, |
0x802c, 0xffffffff, 0x40000000, |
0x915c, 0xffffffff, 0x00010000, |
0x9160, 0xffffffff, 0x00030002, |
0x9178, 0xffffffff, 0x00070000, |
0x917c, 0xffffffff, 0x00030002, |
0x9180, 0xffffffff, 0x00050004, |
0x918c, 0xffffffff, 0x00010006, |
0x9190, 0xffffffff, 0x00090008, |
0x9194, 0xffffffff, 0x00070000, |
0x9198, 0xffffffff, 0x00030002, |
0x919c, 0xffffffff, 0x00050004, |
0x91a8, 0xffffffff, 0x00010006, |
0x91ac, 0xffffffff, 0x00090008, |
0x91b0, 0xffffffff, 0x00070000, |
0x91b4, 0xffffffff, 0x00030002, |
0x91b8, 0xffffffff, 0x00050004, |
0x91c4, 0xffffffff, 0x00010006, |
0x91c8, 0xffffffff, 0x00090008, |
0x91cc, 0xffffffff, 0x00070000, |
0x91d0, 0xffffffff, 0x00030002, |
0x91d4, 0xffffffff, 0x00050004, |
0x91e0, 0xffffffff, 0x00010006, |
0x91e4, 0xffffffff, 0x00090008, |
0x91e8, 0xffffffff, 0x00000000, |
0x91ec, 0xffffffff, 0x00070000, |
0x91f0, 0xffffffff, 0x00030002, |
0x91f4, 0xffffffff, 0x00050004, |
0x9200, 0xffffffff, 0x00010006, |
0x9204, 0xffffffff, 0x00090008, |
0x9208, 0xffffffff, 0x00070000, |
0x920c, 0xffffffff, 0x00030002, |
0x9210, 0xffffffff, 0x00050004, |
0x921c, 0xffffffff, 0x00010006, |
0x9220, 0xffffffff, 0x00090008, |
0x9224, 0xffffffff, 0x00070000, |
0x9228, 0xffffffff, 0x00030002, |
0x922c, 0xffffffff, 0x00050004, |
0x9238, 0xffffffff, 0x00010006, |
0x923c, 0xffffffff, 0x00090008, |
0x9240, 0xffffffff, 0x00070000, |
0x9244, 0xffffffff, 0x00030002, |
0x9248, 0xffffffff, 0x00050004, |
0x9254, 0xffffffff, 0x00010006, |
0x9258, 0xffffffff, 0x00090008, |
0x925c, 0xffffffff, 0x00070000, |
0x9260, 0xffffffff, 0x00030002, |
0x9264, 0xffffffff, 0x00050004, |
0x9270, 0xffffffff, 0x00010006, |
0x9274, 0xffffffff, 0x00090008, |
0x9278, 0xffffffff, 0x00070000, |
0x927c, 0xffffffff, 0x00030002, |
0x9280, 0xffffffff, 0x00050004, |
0x928c, 0xffffffff, 0x00010006, |
0x9290, 0xffffffff, 0x00090008, |
0x9294, 0xffffffff, 0x00000000, |
0x929c, 0xffffffff, 0x00000001, |
0x802c, 0xffffffff, 0xc0000000, |
0x977c, 0xffffffff, 0x00000100, |
0x3f80, 0xffffffff, 0x00000100, |
0xa210, 0xffffffff, 0x00000100, |
0xa214, 0xffffffff, 0x00000100, |
0x4d8, 0xffffffff, 0x00000100, |
0x9784, 0xffffffff, 0x00000100, |
0x9698, 0xffffffff, 0x00000100, |
0x4d4, 0xffffffff, 0x00000200, |
0x30cc, 0xffffffff, 0x00000100, |
0x802c, 0xffffffff, 0xc0000000 |
}; |
static const u32 supersumo_golden_registers[] = |
{ |
0x5eb4, 0xffffffff, 0x00000002, |
0x5cc, 0xffffffff, 0x00000001, |
0x7030, 0xffffffff, 0x00000011, |
0x7c30, 0xffffffff, 0x00000011, |
0x6104, 0x01000300, 0x00000000, |
0x5bc0, 0x00300000, 0x00000000, |
0x8c04, 0xffffffff, 0x40600060, |
0x8c08, 0xffffffff, 0x001c001c, |
0x8c20, 0xffffffff, 0x00800080, |
0x8c24, 0xffffffff, 0x00800080, |
0x8c18, 0xffffffff, 0x20202078, |
0x8c1c, 0xffffffff, 0x00001010, |
0x918c, 0xffffffff, 0x00010006, |
0x91a8, 0xffffffff, 0x00010006, |
0x91c4, 0xffffffff, 0x00010006, |
0x91e0, 0xffffffff, 0x00010006, |
0x9200, 0xffffffff, 0x00010006, |
0x9150, 0xffffffff, 0x6e944040, |
0x917c, 0xffffffff, 0x00030002, |
0x9180, 0xffffffff, 0x00050004, |
0x9198, 0xffffffff, 0x00030002, |
0x919c, 0xffffffff, 0x00050004, |
0x91b4, 0xffffffff, 0x00030002, |
0x91b8, 0xffffffff, 0x00050004, |
0x91d0, 0xffffffff, 0x00030002, |
0x91d4, 0xffffffff, 0x00050004, |
0x91f0, 0xffffffff, 0x00030002, |
0x91f4, 0xffffffff, 0x00050004, |
0x915c, 0xffffffff, 0x00010000, |
0x9160, 0xffffffff, 0x00030002, |
0x3f90, 0xffff0000, 0xff000000, |
0x9178, 0xffffffff, 0x00070000, |
0x9194, 0xffffffff, 0x00070000, |
0x91b0, 0xffffffff, 0x00070000, |
0x91cc, 0xffffffff, 0x00070000, |
0x91ec, 0xffffffff, 0x00070000, |
0x9148, 0xffff0000, 0xff000000, |
0x9190, 0xffffffff, 0x00090008, |
0x91ac, 0xffffffff, 0x00090008, |
0x91c8, 0xffffffff, 0x00090008, |
0x91e4, 0xffffffff, 0x00090008, |
0x9204, 0xffffffff, 0x00090008, |
0x3f94, 0xffff0000, 0xff000000, |
0x914c, 0xffff0000, 0xff000000, |
0x929c, 0xffffffff, 0x00000001, |
0x8a18, 0xffffffff, 0x00000100, |
0x8b28, 0xffffffff, 0x00000100, |
0x9144, 0xffffffff, 0x00000100, |
0x5644, 0xffffffff, 0x00000100, |
0x9b7c, 0xffffffff, 0x00000000, |
0x8030, 0xffffffff, 0x0000100a, |
0x8a14, 0xffffffff, 0x00000007, |
0x8b24, 0xffffffff, 0x00ff0fff, |
0x8b10, 0xffffffff, 0x00000000, |
0x28a4c, 0x06000000, 0x06000000, |
0x4d8, 0xffffffff, 0x00000100, |
0x913c, 0xffff000f, 0x0100000a, |
0x960c, 0xffffffff, 0x54763210, |
0x88c4, 0xffffffff, 0x000000c2, |
0x88d4, 0xffffffff, 0x00000010, |
0x8974, 0xffffffff, 0x00000000, |
0xc78, 0x00000080, 0x00000080, |
0x5e78, 0xffffffff, 0x001000f0, |
0xd02c, 0xffffffff, 0x08421000, |
0xa008, 0xffffffff, 0x00010000, |
0x8d00, 0xffffffff, 0x100e4848, |
0x8d04, 0xffffffff, 0x00164745, |
0x8c00, 0xffffffff, 0xe4000003, |
0x8cf0, 0x1fffffff, 0x08e00620, |
0x28350, 0xffffffff, 0x00000000, |
0x9508, 0xffffffff, 0x00000002 |
}; |
static const u32 sumo_golden_registers[] = |
{ |
0x900c, 0x00ffffff, 0x0017071f, |
0x8c18, 0xffffffff, 0x10101060, |
0x8c1c, 0xffffffff, 0x00001010, |
0x8c30, 0x0000000f, 0x00000005, |
0x9688, 0x0000000f, 0x00000007 |
}; |
static const u32 wrestler_golden_registers[] = |
{ |
0x5eb4, 0xffffffff, 0x00000002, |
0x5cc, 0xffffffff, 0x00000001, |
0x7030, 0xffffffff, 0x00000011, |
0x7c30, 0xffffffff, 0x00000011, |
0x6104, 0x01000300, 0x00000000, |
0x5bc0, 0x00300000, 0x00000000, |
0x918c, 0xffffffff, 0x00010006, |
0x91a8, 0xffffffff, 0x00010006, |
0x9150, 0xffffffff, 0x6e944040, |
0x917c, 0xffffffff, 0x00030002, |
0x9198, 0xffffffff, 0x00030002, |
0x915c, 0xffffffff, 0x00010000, |
0x3f90, 0xffff0000, 0xff000000, |
0x9178, 0xffffffff, 0x00070000, |
0x9194, 0xffffffff, 0x00070000, |
0x9148, 0xffff0000, 0xff000000, |
0x9190, 0xffffffff, 0x00090008, |
0x91ac, 0xffffffff, 0x00090008, |
0x3f94, 0xffff0000, 0xff000000, |
0x914c, 0xffff0000, 0xff000000, |
0x929c, 0xffffffff, 0x00000001, |
0x8a18, 0xffffffff, 0x00000100, |
0x8b28, 0xffffffff, 0x00000100, |
0x9144, 0xffffffff, 0x00000100, |
0x9b7c, 0xffffffff, 0x00000000, |
0x8030, 0xffffffff, 0x0000100a, |
0x8a14, 0xffffffff, 0x00000001, |
0x8b24, 0xffffffff, 0x00ff0fff, |
0x8b10, 0xffffffff, 0x00000000, |
0x28a4c, 0x06000000, 0x06000000, |
0x4d8, 0xffffffff, 0x00000100, |
0x913c, 0xffff000f, 0x0100000a, |
0x960c, 0xffffffff, 0x54763210, |
0x88c4, 0xffffffff, 0x000000c2, |
0x88d4, 0xffffffff, 0x00000010, |
0x8974, 0xffffffff, 0x00000000, |
0xc78, 0x00000080, 0x00000080, |
0x5e78, 0xffffffff, 0x001000f0, |
0xd02c, 0xffffffff, 0x08421000, |
0xa008, 0xffffffff, 0x00010000, |
0x8d00, 0xffffffff, 0x100e4848, |
0x8d04, 0xffffffff, 0x00164745, |
0x8c00, 0xffffffff, 0xe4000003, |
0x8cf0, 0x1fffffff, 0x08e00410, |
0x28350, 0xffffffff, 0x00000000, |
0x9508, 0xffffffff, 0x00000002, |
0x900c, 0xffffffff, 0x0017071f, |
0x8c18, 0xffffffff, 0x10101060, |
0x8c1c, 0xffffffff, 0x00001010 |
}; |
static const u32 barts_golden_registers[] = |
{ |
0x5eb4, 0xffffffff, 0x00000002, |
0x5e78, 0x8f311ff1, 0x001000f0, |
0x3f90, 0xffff0000, 0xff000000, |
0x9148, 0xffff0000, 0xff000000, |
0x3f94, 0xffff0000, 0xff000000, |
0x914c, 0xffff0000, 0xff000000, |
0xc78, 0x00000080, 0x00000080, |
0xbd4, 0x70073777, 0x00010001, |
0xd02c, 0xbfffff1f, 0x08421000, |
0xd0b8, 0x03773777, 0x02011003, |
0x5bc0, 0x00200000, 0x50100000, |
0x98f8, 0x33773777, 0x02011003, |
0x98fc, 0xffffffff, 0x76543210, |
0x7030, 0x31000311, 0x00000011, |
0x2f48, 0x00000007, 0x02011003, |
0x6b28, 0x00000010, 0x00000012, |
0x7728, 0x00000010, 0x00000012, |
0x10328, 0x00000010, 0x00000012, |
0x10f28, 0x00000010, 0x00000012, |
0x11b28, 0x00000010, 0x00000012, |
0x12728, 0x00000010, 0x00000012, |
0x240c, 0x000007ff, 0x00000380, |
0x8a14, 0xf000001f, 0x00000007, |
0x8b24, 0x3fff3fff, 0x00ff0fff, |
0x8b10, 0x0000ff0f, 0x00000000, |
0x28a4c, 0x07ffffff, 0x06000000, |
0x10c, 0x00000001, 0x00010003, |
0xa02c, 0xffffffff, 0x0000009b, |
0x913c, 0x0000000f, 0x0100000a, |
0x8d00, 0xffff7f7f, 0x100e4848, |
0x8d04, 0x00ffffff, 0x00164745, |
0x8c00, 0xfffc0003, 0xe4000003, |
0x8c04, 0xf8ff00ff, 0x40600060, |
0x8c08, 0x00ff00ff, 0x001c001c, |
0x8cf0, 0x1fff1fff, 0x08e00620, |
0x8c20, 0x0fff0fff, 0x00800080, |
0x8c24, 0x0fff0fff, 0x00800080, |
0x8c18, 0xffffffff, 0x20202078, |
0x8c1c, 0x0000ffff, 0x00001010, |
0x28350, 0x00000f01, 0x00000000, |
0x9508, 0x3700001f, 0x00000002, |
0x960c, 0xffffffff, 0x54763210, |
0x88c4, 0x001f3ae3, 0x000000c2, |
0x88d4, 0x0000001f, 0x00000010, |
0x8974, 0xffffffff, 0x00000000 |
}; |
static const u32 turks_golden_registers[] = |
{ |
0x5eb4, 0xffffffff, 0x00000002, |
0x5e78, 0x8f311ff1, 0x001000f0, |
0x8c8, 0x00003000, 0x00001070, |
0x8cc, 0x000fffff, 0x00040035, |
0x3f90, 0xffff0000, 0xfff00000, |
0x9148, 0xffff0000, 0xfff00000, |
0x3f94, 0xffff0000, 0xfff00000, |
0x914c, 0xffff0000, 0xfff00000, |
0xc78, 0x00000080, 0x00000080, |
0xbd4, 0x00073007, 0x00010002, |
0xd02c, 0xbfffff1f, 0x08421000, |
0xd0b8, 0x03773777, 0x02010002, |
0x5bc0, 0x00200000, 0x50100000, |
0x98f8, 0x33773777, 0x00010002, |
0x98fc, 0xffffffff, 0x33221100, |
0x7030, 0x31000311, 0x00000011, |
0x2f48, 0x33773777, 0x00010002, |
0x6b28, 0x00000010, 0x00000012, |
0x7728, 0x00000010, 0x00000012, |
0x10328, 0x00000010, 0x00000012, |
0x10f28, 0x00000010, 0x00000012, |
0x11b28, 0x00000010, 0x00000012, |
0x12728, 0x00000010, 0x00000012, |
0x240c, 0x000007ff, 0x00000380, |
0x8a14, 0xf000001f, 0x00000007, |
0x8b24, 0x3fff3fff, 0x00ff0fff, |
0x8b10, 0x0000ff0f, 0x00000000, |
0x28a4c, 0x07ffffff, 0x06000000, |
0x10c, 0x00000001, 0x00010003, |
0xa02c, 0xffffffff, 0x0000009b, |
0x913c, 0x0000000f, 0x0100000a, |
0x8d00, 0xffff7f7f, 0x100e4848, |
0x8d04, 0x00ffffff, 0x00164745, |
0x8c00, 0xfffc0003, 0xe4000003, |
0x8c04, 0xf8ff00ff, 0x40600060, |
0x8c08, 0x00ff00ff, 0x001c001c, |
0x8cf0, 0x1fff1fff, 0x08e00410, |
0x8c20, 0x0fff0fff, 0x00800080, |
0x8c24, 0x0fff0fff, 0x00800080, |
0x8c18, 0xffffffff, 0x20202078, |
0x8c1c, 0x0000ffff, 0x00001010, |
0x28350, 0x00000f01, 0x00000000, |
0x9508, 0x3700001f, 0x00000002, |
0x960c, 0xffffffff, 0x54763210, |
0x88c4, 0x001f3ae3, 0x000000c2, |
0x88d4, 0x0000001f, 0x00000010, |
0x8974, 0xffffffff, 0x00000000 |
}; |
static const u32 caicos_golden_registers[] = |
{ |
0x5eb4, 0xffffffff, 0x00000002, |
0x5e78, 0x8f311ff1, 0x001000f0, |
0x8c8, 0x00003420, 0x00001450, |
0x8cc, 0x000fffff, 0x00040035, |
0x3f90, 0xffff0000, 0xfffc0000, |
0x9148, 0xffff0000, 0xfffc0000, |
0x3f94, 0xffff0000, 0xfffc0000, |
0x914c, 0xffff0000, 0xfffc0000, |
0xc78, 0x00000080, 0x00000080, |
0xbd4, 0x00073007, 0x00010001, |
0xd02c, 0xbfffff1f, 0x08421000, |
0xd0b8, 0x03773777, 0x02010001, |
0x5bc0, 0x00200000, 0x50100000, |
0x98f8, 0x33773777, 0x02010001, |
0x98fc, 0xffffffff, 0x33221100, |
0x7030, 0x31000311, 0x00000011, |
0x2f48, 0x33773777, 0x02010001, |
0x6b28, 0x00000010, 0x00000012, |
0x7728, 0x00000010, 0x00000012, |
0x10328, 0x00000010, 0x00000012, |
0x10f28, 0x00000010, 0x00000012, |
0x11b28, 0x00000010, 0x00000012, |
0x12728, 0x00000010, 0x00000012, |
0x240c, 0x000007ff, 0x00000380, |
0x8a14, 0xf000001f, 0x00000001, |
0x8b24, 0x3fff3fff, 0x00ff0fff, |
0x8b10, 0x0000ff0f, 0x00000000, |
0x28a4c, 0x07ffffff, 0x06000000, |
0x10c, 0x00000001, 0x00010003, |
0xa02c, 0xffffffff, 0x0000009b, |
0x913c, 0x0000000f, 0x0100000a, |
0x8d00, 0xffff7f7f, 0x100e4848, |
0x8d04, 0x00ffffff, 0x00164745, |
0x8c00, 0xfffc0003, 0xe4000003, |
0x8c04, 0xf8ff00ff, 0x40600060, |
0x8c08, 0x00ff00ff, 0x001c001c, |
0x8cf0, 0x1fff1fff, 0x08e00410, |
0x8c20, 0x0fff0fff, 0x00800080, |
0x8c24, 0x0fff0fff, 0x00800080, |
0x8c18, 0xffffffff, 0x20202078, |
0x8c1c, 0x0000ffff, 0x00001010, |
0x28350, 0x00000f01, 0x00000000, |
0x9508, 0x3700001f, 0x00000002, |
0x960c, 0xffffffff, 0x54763210, |
0x88c4, 0x001f3ae3, 0x000000c2, |
0x88d4, 0x0000001f, 0x00000010, |
0x8974, 0xffffffff, 0x00000000 |
}; |
static void evergreen_init_golden_registers(struct radeon_device *rdev) |
{ |
switch (rdev->family) { |
case CHIP_CYPRESS: |
case CHIP_HEMLOCK: |
radeon_program_register_sequence(rdev, |
evergreen_golden_registers, |
(const u32)ARRAY_SIZE(evergreen_golden_registers)); |
radeon_program_register_sequence(rdev, |
evergreen_golden_registers2, |
(const u32)ARRAY_SIZE(evergreen_golden_registers2)); |
radeon_program_register_sequence(rdev, |
cypress_mgcg_init, |
(const u32)ARRAY_SIZE(cypress_mgcg_init)); |
break; |
case CHIP_JUNIPER: |
radeon_program_register_sequence(rdev, |
evergreen_golden_registers, |
(const u32)ARRAY_SIZE(evergreen_golden_registers)); |
radeon_program_register_sequence(rdev, |
evergreen_golden_registers2, |
(const u32)ARRAY_SIZE(evergreen_golden_registers2)); |
radeon_program_register_sequence(rdev, |
juniper_mgcg_init, |
(const u32)ARRAY_SIZE(juniper_mgcg_init)); |
break; |
case CHIP_REDWOOD: |
radeon_program_register_sequence(rdev, |
evergreen_golden_registers, |
(const u32)ARRAY_SIZE(evergreen_golden_registers)); |
radeon_program_register_sequence(rdev, |
evergreen_golden_registers2, |
(const u32)ARRAY_SIZE(evergreen_golden_registers2)); |
radeon_program_register_sequence(rdev, |
redwood_mgcg_init, |
(const u32)ARRAY_SIZE(redwood_mgcg_init)); |
break; |
case CHIP_CEDAR: |
radeon_program_register_sequence(rdev, |
cedar_golden_registers, |
(const u32)ARRAY_SIZE(cedar_golden_registers)); |
radeon_program_register_sequence(rdev, |
evergreen_golden_registers2, |
(const u32)ARRAY_SIZE(evergreen_golden_registers2)); |
radeon_program_register_sequence(rdev, |
cedar_mgcg_init, |
(const u32)ARRAY_SIZE(cedar_mgcg_init)); |
break; |
case CHIP_PALM: |
radeon_program_register_sequence(rdev, |
wrestler_golden_registers, |
(const u32)ARRAY_SIZE(wrestler_golden_registers)); |
break; |
case CHIP_SUMO: |
radeon_program_register_sequence(rdev, |
supersumo_golden_registers, |
(const u32)ARRAY_SIZE(supersumo_golden_registers)); |
break; |
case CHIP_SUMO2: |
radeon_program_register_sequence(rdev, |
supersumo_golden_registers, |
(const u32)ARRAY_SIZE(supersumo_golden_registers)); |
radeon_program_register_sequence(rdev, |
sumo_golden_registers, |
(const u32)ARRAY_SIZE(sumo_golden_registers)); |
break; |
case CHIP_BARTS: |
radeon_program_register_sequence(rdev, |
barts_golden_registers, |
(const u32)ARRAY_SIZE(barts_golden_registers)); |
break; |
case CHIP_TURKS: |
radeon_program_register_sequence(rdev, |
turks_golden_registers, |
(const u32)ARRAY_SIZE(turks_golden_registers)); |
break; |
case CHIP_CAICOS: |
radeon_program_register_sequence(rdev, |
caicos_golden_registers, |
(const u32)ARRAY_SIZE(caicos_golden_registers)); |
break; |
default: |
break; |
} |
} |
void evergreen_tiling_fields(unsigned tiling_flags, unsigned *bankw, |
unsigned *bankh, unsigned *mtaspect, |
unsigned *tile_split) |
84,6 → 942,142 |
} |
} |
static int sumo_set_uvd_clock(struct radeon_device *rdev, u32 clock, |
u32 cntl_reg, u32 status_reg) |
{ |
int r, i; |
struct atom_clock_dividers dividers; |
r = radeon_atom_get_clock_dividers(rdev, COMPUTE_ENGINE_PLL_PARAM, |
clock, false, ÷rs); |
if (r) |
return r; |
WREG32_P(cntl_reg, dividers.post_div, ~(DCLK_DIR_CNTL_EN|DCLK_DIVIDER_MASK)); |
for (i = 0; i < 100; i++) { |
if (RREG32(status_reg) & DCLK_STATUS) |
break; |
mdelay(10); |
} |
if (i == 100) |
return -ETIMEDOUT; |
return 0; |
} |
int sumo_set_uvd_clocks(struct radeon_device *rdev, u32 vclk, u32 dclk) |
{ |
int r = 0; |
u32 cg_scratch = RREG32(CG_SCRATCH1); |
r = sumo_set_uvd_clock(rdev, vclk, CG_VCLK_CNTL, CG_VCLK_STATUS); |
if (r) |
goto done; |
cg_scratch &= 0xffff0000; |
cg_scratch |= vclk / 100; /* Mhz */ |
r = sumo_set_uvd_clock(rdev, dclk, CG_DCLK_CNTL, CG_DCLK_STATUS); |
if (r) |
goto done; |
cg_scratch &= 0x0000ffff; |
cg_scratch |= (dclk / 100) << 16; /* Mhz */ |
done: |
WREG32(CG_SCRATCH1, cg_scratch); |
return r; |
} |
int evergreen_set_uvd_clocks(struct radeon_device *rdev, u32 vclk, u32 dclk) |
{ |
/* start off with something large */ |
unsigned fb_div = 0, vclk_div = 0, dclk_div = 0; |
int r; |
/* bypass vclk and dclk with bclk */ |
WREG32_P(CG_UPLL_FUNC_CNTL_2, |
VCLK_SRC_SEL(1) | DCLK_SRC_SEL(1), |
~(VCLK_SRC_SEL_MASK | DCLK_SRC_SEL_MASK)); |
/* put PLL in bypass mode */ |
WREG32_P(CG_UPLL_FUNC_CNTL, UPLL_BYPASS_EN_MASK, ~UPLL_BYPASS_EN_MASK); |
if (!vclk || !dclk) { |
/* keep the Bypass mode, put PLL to sleep */ |
WREG32_P(CG_UPLL_FUNC_CNTL, UPLL_SLEEP_MASK, ~UPLL_SLEEP_MASK); |
return 0; |
} |
// r = radeon_uvd_calc_upll_dividers(rdev, vclk, dclk, 125000, 250000, |
// 16384, 0x03FFFFFF, 0, 128, 5, |
// &fb_div, &vclk_div, &dclk_div); |
if (r) |
return r; |
/* set VCO_MODE to 1 */ |
WREG32_P(CG_UPLL_FUNC_CNTL, UPLL_VCO_MODE_MASK, ~UPLL_VCO_MODE_MASK); |
/* toggle UPLL_SLEEP to 1 then back to 0 */ |
WREG32_P(CG_UPLL_FUNC_CNTL, UPLL_SLEEP_MASK, ~UPLL_SLEEP_MASK); |
WREG32_P(CG_UPLL_FUNC_CNTL, 0, ~UPLL_SLEEP_MASK); |
/* deassert UPLL_RESET */ |
WREG32_P(CG_UPLL_FUNC_CNTL, 0, ~UPLL_RESET_MASK); |
mdelay(1); |
// r = radeon_uvd_send_upll_ctlreq(rdev, CG_UPLL_FUNC_CNTL); |
// if (r) |
// return r; |
/* assert UPLL_RESET again */ |
WREG32_P(CG_UPLL_FUNC_CNTL, UPLL_RESET_MASK, ~UPLL_RESET_MASK); |
/* disable spread spectrum. */ |
WREG32_P(CG_UPLL_SPREAD_SPECTRUM, 0, ~SSEN_MASK); |
/* set feedback divider */ |
WREG32_P(CG_UPLL_FUNC_CNTL_3, UPLL_FB_DIV(fb_div), ~UPLL_FB_DIV_MASK); |
/* set ref divider to 0 */ |
WREG32_P(CG_UPLL_FUNC_CNTL, 0, ~UPLL_REF_DIV_MASK); |
if (fb_div < 307200) |
WREG32_P(CG_UPLL_FUNC_CNTL_4, 0, ~UPLL_SPARE_ISPARE9); |
else |
WREG32_P(CG_UPLL_FUNC_CNTL_4, UPLL_SPARE_ISPARE9, ~UPLL_SPARE_ISPARE9); |
/* set PDIV_A and PDIV_B */ |
WREG32_P(CG_UPLL_FUNC_CNTL_2, |
UPLL_PDIV_A(vclk_div) | UPLL_PDIV_B(dclk_div), |
~(UPLL_PDIV_A_MASK | UPLL_PDIV_B_MASK)); |
/* give the PLL some time to settle */ |
mdelay(15); |
/* deassert PLL_RESET */ |
WREG32_P(CG_UPLL_FUNC_CNTL, 0, ~UPLL_RESET_MASK); |
mdelay(15); |
/* switch from bypass mode to normal mode */ |
WREG32_P(CG_UPLL_FUNC_CNTL, 0, ~UPLL_BYPASS_EN_MASK); |
// r = radeon_uvd_send_upll_ctlreq(rdev, CG_UPLL_FUNC_CNTL); |
// if (r) |
// return r; |
/* switch VCLK and DCLK selection */ |
WREG32_P(CG_UPLL_FUNC_CNTL_2, |
VCLK_SRC_SEL(2) | DCLK_SRC_SEL(2), |
~(VCLK_SRC_SEL_MASK | DCLK_SRC_SEL_MASK)); |
mdelay(100); |
return 0; |
} |
void evergreen_fix_pci_max_read_req_size(struct radeon_device *rdev) |
{ |
u16 ctl, v; |
105,6 → 1099,27 |
} |
} |
static bool dce4_is_in_vblank(struct radeon_device *rdev, int crtc) |
{ |
if (RREG32(EVERGREEN_CRTC_STATUS + crtc_offsets[crtc]) & EVERGREEN_CRTC_V_BLANK) |
return true; |
else |
return false; |
} |
static bool dce4_is_counter_moving(struct radeon_device *rdev, int crtc) |
{ |
u32 pos1, pos2; |
pos1 = RREG32(EVERGREEN_CRTC_STATUS_POSITION + crtc_offsets[crtc]); |
pos2 = RREG32(EVERGREEN_CRTC_STATUS_POSITION + crtc_offsets[crtc]); |
if (pos1 != pos2) |
return true; |
else |
return false; |
} |
/** |
* dce4_wait_for_vblank - vblank wait asic callback. |
* |
115,21 → 1130,28 |
*/ |
void dce4_wait_for_vblank(struct radeon_device *rdev, int crtc) |
{ |
int i; |
unsigned i = 0; |
if (crtc >= rdev->num_crtc) |
return; |
if (RREG32(EVERGREEN_CRTC_CONTROL + crtc_offsets[crtc]) & EVERGREEN_CRTC_MASTER_EN) { |
for (i = 0; i < rdev->usec_timeout; i++) { |
if (!(RREG32(EVERGREEN_CRTC_STATUS + crtc_offsets[crtc]) & EVERGREEN_CRTC_V_BLANK)) |
if (!(RREG32(EVERGREEN_CRTC_CONTROL + crtc_offsets[crtc]) & EVERGREEN_CRTC_MASTER_EN)) |
return; |
/* depending on when we hit vblank, we may be close to active; if so, |
* wait for another frame. |
*/ |
while (dce4_is_in_vblank(rdev, crtc)) { |
if (i++ % 100 == 0) { |
if (!dce4_is_counter_moving(rdev, crtc)) |
break; |
udelay(1); |
} |
for (i = 0; i < rdev->usec_timeout; i++) { |
if (RREG32(EVERGREEN_CRTC_STATUS + crtc_offsets[crtc]) & EVERGREEN_CRTC_V_BLANK) |
} |
while (!dce4_is_in_vblank(rdev, crtc)) { |
if (i++ % 100 == 0) { |
if (!dce4_is_counter_moving(rdev, crtc)) |
break; |
udelay(1); |
} |
} |
} |
293,6 → 1315,64 |
} |
/** |
* btc_pm_init_profile - Initialize power profiles callback. |
* |
* @rdev: radeon_device pointer |
* |
* Initialize the power states used in profile mode |
* (BTC, cayman). |
* Used for profile mode only. |
*/ |
void btc_pm_init_profile(struct radeon_device *rdev) |
{ |
int idx; |
/* default */ |
rdev->pm.profiles[PM_PROFILE_DEFAULT_IDX].dpms_off_ps_idx = rdev->pm.default_power_state_index; |
rdev->pm.profiles[PM_PROFILE_DEFAULT_IDX].dpms_on_ps_idx = rdev->pm.default_power_state_index; |
rdev->pm.profiles[PM_PROFILE_DEFAULT_IDX].dpms_off_cm_idx = 0; |
rdev->pm.profiles[PM_PROFILE_DEFAULT_IDX].dpms_on_cm_idx = 2; |
/* starting with BTC, there is one state that is used for both |
* MH and SH. Difference is that we always use the high clock index for |
* mclk. |
*/ |
if (rdev->flags & RADEON_IS_MOBILITY) |
idx = radeon_pm_get_type_index(rdev, POWER_STATE_TYPE_BATTERY, 0); |
else |
idx = radeon_pm_get_type_index(rdev, POWER_STATE_TYPE_PERFORMANCE, 0); |
/* low sh */ |
rdev->pm.profiles[PM_PROFILE_LOW_SH_IDX].dpms_off_ps_idx = idx; |
rdev->pm.profiles[PM_PROFILE_LOW_SH_IDX].dpms_on_ps_idx = idx; |
rdev->pm.profiles[PM_PROFILE_LOW_SH_IDX].dpms_off_cm_idx = 0; |
rdev->pm.profiles[PM_PROFILE_LOW_SH_IDX].dpms_on_cm_idx = 0; |
/* mid sh */ |
rdev->pm.profiles[PM_PROFILE_MID_SH_IDX].dpms_off_ps_idx = idx; |
rdev->pm.profiles[PM_PROFILE_MID_SH_IDX].dpms_on_ps_idx = idx; |
rdev->pm.profiles[PM_PROFILE_MID_SH_IDX].dpms_off_cm_idx = 0; |
rdev->pm.profiles[PM_PROFILE_MID_SH_IDX].dpms_on_cm_idx = 1; |
/* high sh */ |
rdev->pm.profiles[PM_PROFILE_HIGH_SH_IDX].dpms_off_ps_idx = idx; |
rdev->pm.profiles[PM_PROFILE_HIGH_SH_IDX].dpms_on_ps_idx = idx; |
rdev->pm.profiles[PM_PROFILE_HIGH_SH_IDX].dpms_off_cm_idx = 0; |
rdev->pm.profiles[PM_PROFILE_HIGH_SH_IDX].dpms_on_cm_idx = 2; |
/* low mh */ |
rdev->pm.profiles[PM_PROFILE_LOW_MH_IDX].dpms_off_ps_idx = idx; |
rdev->pm.profiles[PM_PROFILE_LOW_MH_IDX].dpms_on_ps_idx = idx; |
rdev->pm.profiles[PM_PROFILE_LOW_MH_IDX].dpms_off_cm_idx = 0; |
rdev->pm.profiles[PM_PROFILE_LOW_MH_IDX].dpms_on_cm_idx = 0; |
/* mid mh */ |
rdev->pm.profiles[PM_PROFILE_MID_MH_IDX].dpms_off_ps_idx = idx; |
rdev->pm.profiles[PM_PROFILE_MID_MH_IDX].dpms_on_ps_idx = idx; |
rdev->pm.profiles[PM_PROFILE_MID_MH_IDX].dpms_off_cm_idx = 0; |
rdev->pm.profiles[PM_PROFILE_MID_MH_IDX].dpms_on_cm_idx = 1; |
/* high mh */ |
rdev->pm.profiles[PM_PROFILE_HIGH_MH_IDX].dpms_off_ps_idx = idx; |
rdev->pm.profiles[PM_PROFILE_HIGH_MH_IDX].dpms_on_ps_idx = idx; |
rdev->pm.profiles[PM_PROFILE_HIGH_MH_IDX].dpms_off_cm_idx = 0; |
rdev->pm.profiles[PM_PROFILE_HIGH_MH_IDX].dpms_on_cm_idx = 2; |
} |
/** |
* evergreen_pm_misc - set additional pm hw parameters callback. |
* |
* @rdev: radeon_device pointer |
316,6 → 1396,19 |
rdev->pm.current_vddc = voltage->voltage; |
DRM_DEBUG("Setting: vddc: %d\n", voltage->voltage); |
} |
/* starting with BTC, there is one state that is used for both |
* MH and SH. Difference is that we always use the high clock index for |
* mclk and vddci. |
*/ |
if ((rdev->pm.pm_method == PM_METHOD_PROFILE) && |
(rdev->family >= CHIP_BARTS) && |
rdev->pm.active_crtc_count && |
((rdev->pm.profile_index == PM_PROFILE_MID_MH_IDX) || |
(rdev->pm.profile_index == PM_PROFILE_LOW_MH_IDX))) |
voltage = &rdev->pm.power_state[req_ps_idx]. |
clock_info[rdev->pm.profiles[PM_PROFILE_HIGH_MH_IDX].dpms_on_cm_idx].voltage; |
/* 0xff01 is a flag rather then an actual voltage */ |
if (voltage->vddci == 0xff01) |
return; |
508,6 → 1601,16 |
list_for_each_entry(connector, &dev->mode_config.connector_list, head) { |
struct radeon_connector *radeon_connector = to_radeon_connector(connector); |
if (connector->connector_type == DRM_MODE_CONNECTOR_eDP || |
connector->connector_type == DRM_MODE_CONNECTOR_LVDS) { |
/* don't try to enable hpd on eDP or LVDS avoid breaking the |
* aux dp channel on imac and help (but not completely fix) |
* https://bugzilla.redhat.com/show_bug.cgi?id=726143 |
* also avoid interrupt storms during dpms. |
*/ |
continue; |
} |
switch (radeon_connector->hpd.hpd) { |
case RADEON_HPD_1: |
WREG32(DC_HPD1_CONTROL, tmp); |
1211,11 → 2314,13 |
u32 crtc_enabled, tmp, frame_count, blackout; |
int i, j; |
if (!ASIC_IS_NODCE(rdev)) { |
save->vga_render_control = RREG32(VGA_RENDER_CONTROL); |
save->vga_hdp_control = RREG32(VGA_HDP_CONTROL); |
/* disable VGA render */ |
WREG32(VGA_RENDER_CONTROL, 0); |
} |
/* blank the display controllers */ |
for (i = 0; i < rdev->num_crtc; i++) { |
crtc_enabled = RREG32(EVERGREEN_CRTC_CONTROL + crtc_offsets[i]) & EVERGREEN_CRTC_MASTER_EN; |
1225,6 → 2330,7 |
tmp = RREG32(EVERGREEN_CRTC_BLANK_CONTROL + crtc_offsets[i]); |
if (!(tmp & EVERGREEN_CRTC_BLANK_DATA_EN)) { |
radeon_wait_for_vblank(rdev, i); |
WREG32(EVERGREEN_CRTC_UPDATE_LOCK + crtc_offsets[i], 1); |
tmp |= EVERGREEN_CRTC_BLANK_DATA_EN; |
WREG32(EVERGREEN_CRTC_BLANK_CONTROL + crtc_offsets[i], tmp); |
} |
1232,8 → 2338,10 |
tmp = RREG32(EVERGREEN_CRTC_CONTROL + crtc_offsets[i]); |
if (!(tmp & EVERGREEN_CRTC_DISP_READ_REQUEST_DISABLE)) { |
radeon_wait_for_vblank(rdev, i); |
WREG32(EVERGREEN_CRTC_UPDATE_LOCK + crtc_offsets[i], 1); |
tmp |= EVERGREEN_CRTC_DISP_READ_REQUEST_DISABLE; |
WREG32(EVERGREEN_CRTC_CONTROL + crtc_offsets[i], tmp); |
WREG32(EVERGREEN_CRTC_UPDATE_LOCK + crtc_offsets[i], 0); |
} |
} |
/* wait for the next frame */ |
1243,6 → 2351,15 |
break; |
udelay(1); |
} |
/* XXX this is a hack to avoid strange behavior with EFI on certain systems */ |
WREG32(EVERGREEN_CRTC_UPDATE_LOCK + crtc_offsets[i], 1); |
tmp = RREG32(EVERGREEN_CRTC_CONTROL + crtc_offsets[i]); |
tmp &= ~EVERGREEN_CRTC_MASTER_EN; |
WREG32(EVERGREEN_CRTC_CONTROL + crtc_offsets[i], tmp); |
WREG32(EVERGREEN_CRTC_UPDATE_LOCK + crtc_offsets[i], 0); |
save->crtc_enabled[i] = false; |
/* ***** */ |
} else { |
save->crtc_enabled[i] = false; |
} |
1258,7 → 2375,25 |
blackout &= ~BLACKOUT_MODE_MASK; |
WREG32(MC_SHARED_BLACKOUT_CNTL, blackout | 1); |
} |
/* wait for the MC to settle */ |
udelay(100); |
/* lock double buffered regs */ |
for (i = 0; i < rdev->num_crtc; i++) { |
if (save->crtc_enabled[i]) { |
tmp = RREG32(EVERGREEN_GRPH_UPDATE + crtc_offsets[i]); |
if (!(tmp & EVERGREEN_GRPH_UPDATE_LOCK)) { |
tmp |= EVERGREEN_GRPH_UPDATE_LOCK; |
WREG32(EVERGREEN_GRPH_UPDATE + crtc_offsets[i], tmp); |
} |
tmp = RREG32(EVERGREEN_MASTER_UPDATE_LOCK + crtc_offsets[i]); |
if (!(tmp & 1)) { |
tmp |= 1; |
WREG32(EVERGREEN_MASTER_UPDATE_LOCK + crtc_offsets[i], tmp); |
} |
} |
} |
} |
void evergreen_mc_resume(struct radeon_device *rdev, struct evergreen_mc_save *save) |
{ |
1276,9 → 2411,39 |
WREG32(EVERGREEN_GRPH_SECONDARY_SURFACE_ADDRESS + crtc_offsets[i], |
(u32)rdev->mc.vram_start); |
} |
if (!ASIC_IS_NODCE(rdev)) { |
WREG32(EVERGREEN_VGA_MEMORY_BASE_ADDRESS_HIGH, upper_32_bits(rdev->mc.vram_start)); |
WREG32(EVERGREEN_VGA_MEMORY_BASE_ADDRESS, (u32)rdev->mc.vram_start); |
} |
/* unlock regs and wait for update */ |
for (i = 0; i < rdev->num_crtc; i++) { |
if (save->crtc_enabled[i]) { |
tmp = RREG32(EVERGREEN_MASTER_UPDATE_MODE + crtc_offsets[i]); |
if ((tmp & 0x3) != 0) { |
tmp &= ~0x3; |
WREG32(EVERGREEN_MASTER_UPDATE_MODE + crtc_offsets[i], tmp); |
} |
tmp = RREG32(EVERGREEN_GRPH_UPDATE + crtc_offsets[i]); |
if (tmp & EVERGREEN_GRPH_UPDATE_LOCK) { |
tmp &= ~EVERGREEN_GRPH_UPDATE_LOCK; |
WREG32(EVERGREEN_GRPH_UPDATE + crtc_offsets[i], tmp); |
} |
tmp = RREG32(EVERGREEN_MASTER_UPDATE_LOCK + crtc_offsets[i]); |
if (tmp & 1) { |
tmp &= ~1; |
WREG32(EVERGREEN_MASTER_UPDATE_LOCK + crtc_offsets[i], tmp); |
} |
for (j = 0; j < rdev->usec_timeout; j++) { |
tmp = RREG32(EVERGREEN_GRPH_UPDATE + crtc_offsets[i]); |
if ((tmp & EVERGREEN_GRPH_SURFACE_UPDATE_PENDING) == 0) |
break; |
udelay(1); |
} |
} |
} |
/* unblackout the MC */ |
tmp = RREG32(MC_SHARED_BLACKOUT_CNTL); |
tmp &= ~BLACKOUT_MODE_MASK; |
1291,11 → 2456,15 |
if (ASIC_IS_DCE6(rdev)) { |
tmp = RREG32(EVERGREEN_CRTC_BLANK_CONTROL + crtc_offsets[i]); |
tmp |= EVERGREEN_CRTC_BLANK_DATA_EN; |
WREG32(EVERGREEN_CRTC_UPDATE_LOCK + crtc_offsets[i], 1); |
WREG32(EVERGREEN_CRTC_BLANK_CONTROL + crtc_offsets[i], tmp); |
WREG32(EVERGREEN_CRTC_UPDATE_LOCK + crtc_offsets[i], 0); |
} else { |
tmp = RREG32(EVERGREEN_CRTC_CONTROL + crtc_offsets[i]); |
tmp &= ~EVERGREEN_CRTC_DISP_READ_REQUEST_DISABLE; |
WREG32(EVERGREEN_CRTC_UPDATE_LOCK + crtc_offsets[i], 1); |
WREG32(EVERGREEN_CRTC_CONTROL + crtc_offsets[i], tmp); |
WREG32(EVERGREEN_CRTC_UPDATE_LOCK + crtc_offsets[i], 0); |
} |
/* wait for the next frame */ |
frame_count = radeon_get_vblank_counter(rdev, i); |
1306,11 → 2475,13 |
} |
} |
} |
if (!ASIC_IS_NODCE(rdev)) { |
/* Unlock vga access */ |
WREG32(VGA_HDP_CONTROL, save->vga_hdp_control); |
mdelay(1); |
WREG32(VGA_RENDER_CONTROL, save->vga_render_control); |
} |
} |
void evergreen_mc_program(struct radeon_device *rdev) |
{ |
1940,6 → 3111,14 |
} |
/* enabled rb are just the one not disabled :) */ |
disabled_rb_mask = tmp; |
tmp = 0; |
for (i = 0; i < rdev->config.evergreen.max_backends; i++) |
tmp |= (1 << i); |
/* if all the backends are disabled, fix it up here */ |
if ((disabled_rb_mask & tmp) == tmp) { |
for (i = 0; i < rdev->config.evergreen.max_backends; i++) |
disabled_rb_mask &= ~(1 << i); |
} |
WREG32(GRBM_GFX_INDEX, INSTANCE_BROADCAST_WRITES | SE_BROADCAST_WRITES); |
WREG32(RLC_GFX_INDEX, INSTANCE_BROADCAST_WRITES | SE_BROADCAST_WRITES); |
1948,10 → 3127,24 |
WREG32(DMIF_ADDR_CONFIG, gb_addr_config); |
WREG32(HDP_ADDR_CONFIG, gb_addr_config); |
WREG32(DMA_TILING_CONFIG, gb_addr_config); |
WREG32(UVD_UDEC_ADDR_CONFIG, gb_addr_config); |
WREG32(UVD_UDEC_DB_ADDR_CONFIG, gb_addr_config); |
WREG32(UVD_UDEC_DBW_ADDR_CONFIG, gb_addr_config); |
if ((rdev->config.evergreen.max_backends == 1) && |
(rdev->flags & RADEON_IS_IGP)) { |
if ((disabled_rb_mask & 3) == 1) { |
/* RB0 disabled, RB1 enabled */ |
tmp = 0x11111111; |
} else { |
/* RB1 disabled, RB0 enabled */ |
tmp = 0x00000000; |
} |
} else { |
tmp = gb_addr_config & NUM_PIPES_MASK; |
tmp = r6xx_remap_render_backend(rdev, tmp, rdev->config.evergreen.max_backends, |
EVERGREEN_MAX_BACKENDS, disabled_rb_mask); |
} |
WREG32(GB_BACKEND_MAP, tmp); |
WREG32(CGTS_SYS_TCC_DISABLE, 0); |
2190,8 → 3383,8 |
rdev->mc.real_vram_size = RREG32(CONFIG_MEMSIZE); |
} else { |
/* size in MB on evergreen/cayman/tn */ |
rdev->mc.mc_vram_size = RREG32(CONFIG_MEMSIZE) * 1024 * 1024; |
rdev->mc.real_vram_size = RREG32(CONFIG_MEMSIZE) * 1024 * 1024; |
rdev->mc.mc_vram_size = RREG32(CONFIG_MEMSIZE) * 1024ULL * 1024ULL; |
rdev->mc.real_vram_size = RREG32(CONFIG_MEMSIZE) * 1024ULL * 1024ULL; |
} |
rdev->mc.visible_vram_size = rdev->mc.aper_size; |
r700_vram_gtt_location(rdev, &rdev->mc); |
2200,34 → 3393,8 |
return 0; |
} |
bool evergreen_gpu_is_lockup(struct radeon_device *rdev, struct radeon_ring *ring) |
void evergreen_print_gpu_status_regs(struct radeon_device *rdev) |
{ |
u32 srbm_status; |
u32 grbm_status; |
u32 grbm_status_se0, grbm_status_se1; |
srbm_status = RREG32(SRBM_STATUS); |
grbm_status = RREG32(GRBM_STATUS); |
grbm_status_se0 = RREG32(GRBM_STATUS_SE0); |
grbm_status_se1 = RREG32(GRBM_STATUS_SE1); |
if (!(grbm_status & GUI_ACTIVE)) { |
radeon_ring_lockup_update(ring); |
return false; |
} |
/* force CP activities */ |
radeon_ring_force_activity(rdev, ring); |
return radeon_ring_test_lockup(rdev, ring); |
} |
static int evergreen_gpu_soft_reset(struct radeon_device *rdev) |
{ |
struct evergreen_mc_save save; |
u32 grbm_reset = 0; |
if (!(RREG32(GRBM_STATUS) & GUI_ACTIVE)) |
return 0; |
dev_info(rdev->dev, "GPU softreset \n"); |
dev_info(rdev->dev, " GRBM_STATUS=0x%08X\n", |
RREG32(GRBM_STATUS)); |
dev_info(rdev->dev, " GRBM_STATUS_SE0=0x%08X\n", |
2236,6 → 3403,8 |
RREG32(GRBM_STATUS_SE1)); |
dev_info(rdev->dev, " SRBM_STATUS=0x%08X\n", |
RREG32(SRBM_STATUS)); |
dev_info(rdev->dev, " SRBM_STATUS2 = 0x%08X\n", |
RREG32(SRBM_STATUS2)); |
dev_info(rdev->dev, " R_008674_CP_STALLED_STAT1 = 0x%08X\n", |
RREG32(CP_STALLED_STAT1)); |
dev_info(rdev->dev, " R_008678_CP_STALLED_STAT2 = 0x%08X\n", |
2244,60 → 3413,291 |
RREG32(CP_BUSY_STAT)); |
dev_info(rdev->dev, " R_008680_CP_STAT = 0x%08X\n", |
RREG32(CP_STAT)); |
dev_info(rdev->dev, " R_00D034_DMA_STATUS_REG = 0x%08X\n", |
RREG32(DMA_STATUS_REG)); |
if (rdev->family >= CHIP_CAYMAN) { |
dev_info(rdev->dev, " R_00D834_DMA_STATUS_REG = 0x%08X\n", |
RREG32(DMA_STATUS_REG + 0x800)); |
} |
} |
bool evergreen_is_display_hung(struct radeon_device *rdev) |
{ |
u32 crtc_hung = 0; |
u32 crtc_status[6]; |
u32 i, j, tmp; |
for (i = 0; i < rdev->num_crtc; i++) { |
if (RREG32(EVERGREEN_CRTC_CONTROL + crtc_offsets[i]) & EVERGREEN_CRTC_MASTER_EN) { |
crtc_status[i] = RREG32(EVERGREEN_CRTC_STATUS_HV_COUNT + crtc_offsets[i]); |
crtc_hung |= (1 << i); |
} |
} |
for (j = 0; j < 10; j++) { |
for (i = 0; i < rdev->num_crtc; i++) { |
if (crtc_hung & (1 << i)) { |
tmp = RREG32(EVERGREEN_CRTC_STATUS_HV_COUNT + crtc_offsets[i]); |
if (tmp != crtc_status[i]) |
crtc_hung &= ~(1 << i); |
} |
} |
if (crtc_hung == 0) |
return false; |
udelay(100); |
} |
return true; |
} |
static u32 evergreen_gpu_check_soft_reset(struct radeon_device *rdev) |
{ |
u32 reset_mask = 0; |
u32 tmp; |
/* GRBM_STATUS */ |
tmp = RREG32(GRBM_STATUS); |
if (tmp & (PA_BUSY | SC_BUSY | |
SH_BUSY | SX_BUSY | |
TA_BUSY | VGT_BUSY | |
DB_BUSY | CB_BUSY | |
SPI_BUSY | VGT_BUSY_NO_DMA)) |
reset_mask |= RADEON_RESET_GFX; |
if (tmp & (CF_RQ_PENDING | PF_RQ_PENDING | |
CP_BUSY | CP_COHERENCY_BUSY)) |
reset_mask |= RADEON_RESET_CP; |
if (tmp & GRBM_EE_BUSY) |
reset_mask |= RADEON_RESET_GRBM | RADEON_RESET_GFX | RADEON_RESET_CP; |
/* DMA_STATUS_REG */ |
tmp = RREG32(DMA_STATUS_REG); |
if (!(tmp & DMA_IDLE)) |
reset_mask |= RADEON_RESET_DMA; |
/* SRBM_STATUS2 */ |
tmp = RREG32(SRBM_STATUS2); |
if (tmp & DMA_BUSY) |
reset_mask |= RADEON_RESET_DMA; |
/* SRBM_STATUS */ |
tmp = RREG32(SRBM_STATUS); |
if (tmp & (RLC_RQ_PENDING | RLC_BUSY)) |
reset_mask |= RADEON_RESET_RLC; |
if (tmp & IH_BUSY) |
reset_mask |= RADEON_RESET_IH; |
if (tmp & SEM_BUSY) |
reset_mask |= RADEON_RESET_SEM; |
if (tmp & GRBM_RQ_PENDING) |
reset_mask |= RADEON_RESET_GRBM; |
if (tmp & VMC_BUSY) |
reset_mask |= RADEON_RESET_VMC; |
if (tmp & (MCB_BUSY | MCB_NON_DISPLAY_BUSY | |
MCC_BUSY | MCD_BUSY)) |
reset_mask |= RADEON_RESET_MC; |
if (evergreen_is_display_hung(rdev)) |
reset_mask |= RADEON_RESET_DISPLAY; |
/* VM_L2_STATUS */ |
tmp = RREG32(VM_L2_STATUS); |
if (tmp & L2_BUSY) |
reset_mask |= RADEON_RESET_VMC; |
/* Skip MC reset as it's mostly likely not hung, just busy */ |
if (reset_mask & RADEON_RESET_MC) { |
DRM_DEBUG("MC busy: 0x%08X, clearing.\n", reset_mask); |
reset_mask &= ~RADEON_RESET_MC; |
} |
return reset_mask; |
} |
static void evergreen_gpu_soft_reset(struct radeon_device *rdev, u32 reset_mask) |
{ |
struct evergreen_mc_save save; |
u32 grbm_soft_reset = 0, srbm_soft_reset = 0; |
u32 tmp; |
if (reset_mask == 0) |
return; |
dev_info(rdev->dev, "GPU softreset: 0x%08X\n", reset_mask); |
evergreen_print_gpu_status_regs(rdev); |
/* Disable CP parsing/prefetching */ |
WREG32(CP_ME_CNTL, CP_ME_HALT | CP_PFP_HALT); |
if (reset_mask & RADEON_RESET_DMA) { |
/* Disable DMA */ |
tmp = RREG32(DMA_RB_CNTL); |
tmp &= ~DMA_RB_ENABLE; |
WREG32(DMA_RB_CNTL, tmp); |
} |
udelay(50); |
evergreen_mc_stop(rdev, &save); |
if (evergreen_mc_wait_for_idle(rdev)) { |
dev_warn(rdev->dev, "Wait for MC idle timedout !\n"); |
} |
/* Disable CP parsing/prefetching */ |
WREG32(CP_ME_CNTL, CP_ME_HALT | CP_PFP_HALT); |
/* reset all the gfx blocks */ |
grbm_reset = (SOFT_RESET_CP | |
if (reset_mask & (RADEON_RESET_GFX | RADEON_RESET_COMPUTE)) { |
grbm_soft_reset |= SOFT_RESET_DB | |
SOFT_RESET_CB | |
SOFT_RESET_DB | |
SOFT_RESET_PA | |
SOFT_RESET_SC | |
SOFT_RESET_SPI | |
SOFT_RESET_SX | |
SOFT_RESET_SH | |
SOFT_RESET_SX | |
SOFT_RESET_TC | |
SOFT_RESET_TA | |
SOFT_RESET_VC | |
SOFT_RESET_VGT); |
SOFT_RESET_VGT; |
} |
dev_info(rdev->dev, " GRBM_SOFT_RESET=0x%08X\n", grbm_reset); |
WREG32(GRBM_SOFT_RESET, grbm_reset); |
(void)RREG32(GRBM_SOFT_RESET); |
if (reset_mask & RADEON_RESET_CP) { |
grbm_soft_reset |= SOFT_RESET_CP | |
SOFT_RESET_VGT; |
srbm_soft_reset |= SOFT_RESET_GRBM; |
} |
if (reset_mask & RADEON_RESET_DMA) |
srbm_soft_reset |= SOFT_RESET_DMA; |
if (reset_mask & RADEON_RESET_DISPLAY) |
srbm_soft_reset |= SOFT_RESET_DC; |
if (reset_mask & RADEON_RESET_RLC) |
srbm_soft_reset |= SOFT_RESET_RLC; |
if (reset_mask & RADEON_RESET_SEM) |
srbm_soft_reset |= SOFT_RESET_SEM; |
if (reset_mask & RADEON_RESET_IH) |
srbm_soft_reset |= SOFT_RESET_IH; |
if (reset_mask & RADEON_RESET_GRBM) |
srbm_soft_reset |= SOFT_RESET_GRBM; |
if (reset_mask & RADEON_RESET_VMC) |
srbm_soft_reset |= SOFT_RESET_VMC; |
if (!(rdev->flags & RADEON_IS_IGP)) { |
if (reset_mask & RADEON_RESET_MC) |
srbm_soft_reset |= SOFT_RESET_MC; |
} |
if (grbm_soft_reset) { |
tmp = RREG32(GRBM_SOFT_RESET); |
tmp |= grbm_soft_reset; |
dev_info(rdev->dev, "GRBM_SOFT_RESET=0x%08X\n", tmp); |
WREG32(GRBM_SOFT_RESET, tmp); |
tmp = RREG32(GRBM_SOFT_RESET); |
udelay(50); |
WREG32(GRBM_SOFT_RESET, 0); |
(void)RREG32(GRBM_SOFT_RESET); |
tmp &= ~grbm_soft_reset; |
WREG32(GRBM_SOFT_RESET, tmp); |
tmp = RREG32(GRBM_SOFT_RESET); |
} |
if (srbm_soft_reset) { |
tmp = RREG32(SRBM_SOFT_RESET); |
tmp |= srbm_soft_reset; |
dev_info(rdev->dev, "SRBM_SOFT_RESET=0x%08X\n", tmp); |
WREG32(SRBM_SOFT_RESET, tmp); |
tmp = RREG32(SRBM_SOFT_RESET); |
udelay(50); |
tmp &= ~srbm_soft_reset; |
WREG32(SRBM_SOFT_RESET, tmp); |
tmp = RREG32(SRBM_SOFT_RESET); |
} |
/* Wait a little for things to settle down */ |
udelay(50); |
dev_info(rdev->dev, " GRBM_STATUS=0x%08X\n", |
RREG32(GRBM_STATUS)); |
dev_info(rdev->dev, " GRBM_STATUS_SE0=0x%08X\n", |
RREG32(GRBM_STATUS_SE0)); |
dev_info(rdev->dev, " GRBM_STATUS_SE1=0x%08X\n", |
RREG32(GRBM_STATUS_SE1)); |
dev_info(rdev->dev, " SRBM_STATUS=0x%08X\n", |
RREG32(SRBM_STATUS)); |
dev_info(rdev->dev, " R_008674_CP_STALLED_STAT1 = 0x%08X\n", |
RREG32(CP_STALLED_STAT1)); |
dev_info(rdev->dev, " R_008678_CP_STALLED_STAT2 = 0x%08X\n", |
RREG32(CP_STALLED_STAT2)); |
dev_info(rdev->dev, " R_00867C_CP_BUSY_STAT = 0x%08X\n", |
RREG32(CP_BUSY_STAT)); |
dev_info(rdev->dev, " R_008680_CP_STAT = 0x%08X\n", |
RREG32(CP_STAT)); |
evergreen_mc_resume(rdev, &save); |
return 0; |
udelay(50); |
evergreen_print_gpu_status_regs(rdev); |
} |
int evergreen_asic_reset(struct radeon_device *rdev) |
{ |
return evergreen_gpu_soft_reset(rdev); |
u32 reset_mask; |
reset_mask = evergreen_gpu_check_soft_reset(rdev); |
if (reset_mask) |
r600_set_bios_scratch_engine_hung(rdev, true); |
evergreen_gpu_soft_reset(rdev, reset_mask); |
reset_mask = evergreen_gpu_check_soft_reset(rdev); |
if (!reset_mask) |
r600_set_bios_scratch_engine_hung(rdev, false); |
return 0; |
} |
/** |
* evergreen_gfx_is_lockup - Check if the GFX engine is locked up |
* |
* @rdev: radeon_device pointer |
* @ring: radeon_ring structure holding ring information |
* |
* Check if the GFX engine is locked up. |
* Returns true if the engine appears to be locked up, false if not. |
*/ |
bool evergreen_gfx_is_lockup(struct radeon_device *rdev, struct radeon_ring *ring) |
{ |
u32 reset_mask = evergreen_gpu_check_soft_reset(rdev); |
if (!(reset_mask & (RADEON_RESET_GFX | |
RADEON_RESET_COMPUTE | |
RADEON_RESET_CP))) { |
radeon_ring_lockup_update(ring); |
return false; |
} |
/* force CP activities */ |
radeon_ring_force_activity(rdev, ring); |
return radeon_ring_test_lockup(rdev, ring); |
} |
/** |
* evergreen_dma_is_lockup - Check if the DMA engine is locked up |
* |
* @rdev: radeon_device pointer |
* @ring: radeon_ring structure holding ring information |
* |
* Check if the async DMA engine is locked up. |
* Returns true if the engine appears to be locked up, false if not. |
*/ |
bool evergreen_dma_is_lockup(struct radeon_device *rdev, struct radeon_ring *ring) |
{ |
u32 reset_mask = evergreen_gpu_check_soft_reset(rdev); |
if (!(reset_mask & RADEON_RESET_DMA)) { |
radeon_ring_lockup_update(ring); |
return false; |
} |
/* force ring activities */ |
radeon_ring_force_activity(rdev, ring); |
return radeon_ring_test_lockup(rdev, ring); |
} |
/* Interrupts */ |
u32 evergreen_get_vblank_counter(struct radeon_device *rdev, int crtc) |
3032,6 → 4432,9 |
DRM_ERROR("Unhandled interrupt: %d %d\n", src_id, src_data); |
break; |
} |
case 124: /* UVD */ |
DRM_DEBUG("IH: UVD int: 0x%08x\n", src_data); |
radeon_fence_process(rdev, R600_RING_TYPE_UVD_INDEX); |
break; |
case 146: |
case 147: |
3116,15 → 4519,15 |
struct radeon_ring *ring = &rdev->ring[fence->ring]; |
u64 addr = rdev->fence_drv[fence->ring].gpu_addr; |
/* write the fence */ |
radeon_ring_write(ring, DMA_PACKET(DMA_PACKET_FENCE, 0, 0, 0)); |
radeon_ring_write(ring, DMA_PACKET(DMA_PACKET_FENCE, 0, 0)); |
radeon_ring_write(ring, addr & 0xfffffffc); |
radeon_ring_write(ring, (upper_32_bits(addr) & 0xff)); |
radeon_ring_write(ring, fence->seq); |
/* generate an interrupt */ |
radeon_ring_write(ring, DMA_PACKET(DMA_PACKET_TRAP, 0, 0, 0)); |
radeon_ring_write(ring, DMA_PACKET(DMA_PACKET_TRAP, 0, 0)); |
/* flush HDP */ |
radeon_ring_write(ring, DMA_PACKET(DMA_PACKET_SRBM_WRITE, 0, 0, 0)); |
radeon_ring_write(ring, (0xf << 16) | HDP_MEM_COHERENCY_FLUSH_CNTL); |
radeon_ring_write(ring, DMA_PACKET(DMA_PACKET_SRBM_WRITE, 0, 0)); |
radeon_ring_write(ring, (0xf << 16) | (HDP_MEM_COHERENCY_FLUSH_CNTL >> 2)); |
radeon_ring_write(ring, 1); |
} |
3146,7 → 4549,7 |
while ((next_rptr & 7) != 5) |
next_rptr++; |
next_rptr += 3; |
radeon_ring_write(ring, DMA_PACKET(DMA_PACKET_WRITE, 0, 0, 1)); |
radeon_ring_write(ring, DMA_PACKET(DMA_PACKET_WRITE, 0, 1)); |
radeon_ring_write(ring, ring->next_rptr_gpu_addr & 0xfffffffc); |
radeon_ring_write(ring, upper_32_bits(ring->next_rptr_gpu_addr) & 0xff); |
radeon_ring_write(ring, next_rptr); |
3156,8 → 4559,8 |
* Pad as necessary with NOPs. |
*/ |
while ((ring->wptr & 7) != 5) |
radeon_ring_write(ring, DMA_PACKET(DMA_PACKET_NOP, 0, 0, 0)); |
radeon_ring_write(ring, DMA_PACKET(DMA_PACKET_INDIRECT_BUFFER, 0, 0, 0)); |
radeon_ring_write(ring, DMA_PACKET(DMA_PACKET_NOP, 0, 0)); |
radeon_ring_write(ring, DMA_PACKET(DMA_PACKET_INDIRECT_BUFFER, 0, 0)); |
radeon_ring_write(ring, (ib->gpu_addr & 0xFFFFFFE0)); |
radeon_ring_write(ring, (ib->length_dw << 12) | (upper_32_bits(ib->gpu_addr) & 0xFF)); |
3216,7 → 4619,7 |
if (cur_size_in_dw > 0xFFFFF) |
cur_size_in_dw = 0xFFFFF; |
size_in_dw -= cur_size_in_dw; |
radeon_ring_write(ring, DMA_PACKET(DMA_PACKET_COPY, 0, 0, cur_size_in_dw)); |
radeon_ring_write(ring, DMA_PACKET(DMA_PACKET_COPY, 0, cur_size_in_dw)); |
radeon_ring_write(ring, dst_offset & 0xfffffffc); |
radeon_ring_write(ring, src_offset & 0xfffffffc); |
radeon_ring_write(ring, upper_32_bits(dst_offset) & 0xff); |
3239,7 → 4642,7 |
static int evergreen_startup(struct radeon_device *rdev) |
{ |
struct radeon_ring *ring = &rdev->ring[RADEON_RING_TYPE_GFX_INDEX]; |
struct radeon_ring *ring; |
int r; |
/* enable pcie gen2 link */ |
3306,7 → 4709,24 |
return r; |
} |
// r = rv770_uvd_resume(rdev); |
// if (!r) { |
// r = radeon_fence_driver_start_ring(rdev, |
// R600_RING_TYPE_UVD_INDEX); |
// if (r) |
// dev_err(rdev->dev, "UVD fences init error (%d).\n", r); |
// } |
// if (r) |
// rdev->ring[R600_RING_TYPE_UVD_INDEX].ring_size = 0; |
/* Enable IRQ */ |
if (!rdev->irq.installed) { |
r = radeon_irq_kms_init(rdev); |
if (r) |
return r; |
} |
r = r600_irq_init(rdev); |
if (r) { |
DRM_ERROR("radeon: IH init failed (%d).\n", r); |
3315,6 → 4735,7 |
} |
evergreen_irq_set(rdev); |
ring = &rdev->ring[RADEON_RING_TYPE_GFX_INDEX]; |
r = radeon_ring_init(rdev, ring, ring->ring_size, RADEON_WB_CP_RPTR_OFFSET, |
R600_CP_RB_RPTR, R600_CP_RB_WPTR, |
0, 0xfffff, RADEON_CP_PACKET2); |
3324,7 → 4745,7 |
ring = &rdev->ring[R600_RING_TYPE_DMA_INDEX]; |
r = radeon_ring_init(rdev, ring, ring->ring_size, R600_WB_DMA_RPTR_OFFSET, |
DMA_RB_RPTR, DMA_RB_WPTR, |
2, 0x3fffc, DMA_PACKET(DMA_PACKET_NOP, 0, 0, 0)); |
2, 0x3fffc, DMA_PACKET(DMA_PACKET_NOP, 0, 0)); |
if (r) |
return r; |
3338,6 → 4759,19 |
if (r) |
return r; |
ring = &rdev->ring[R600_RING_TYPE_UVD_INDEX]; |
if (ring->ring_size) { |
r = radeon_ring_init(rdev, ring, ring->ring_size, |
R600_WB_UVD_RPTR_OFFSET, |
UVD_RBC_RB_RPTR, UVD_RBC_RB_WPTR, |
0, 0xfffff, RADEON_CP_PACKET2); |
if (!r) |
r = r600_uvd_init(rdev); |
if (r) |
DRM_ERROR("radeon: error initializing UVD (%d).\n", r); |
} |
r = radeon_ib_pool_init(rdev); |
if (r) { |
dev_err(rdev->dev, "IB initialization failed (%d).\n", r); |
3410,6 → 4844,8 |
DRM_INFO("GPU not posted. posting now...\n"); |
atom_asic_init(rdev->mode_info.atom_context); |
} |
/* init golden registers */ |
evergreen_init_golden_registers(rdev); |
/* Initialize scratch registers */ |
r600_scratch_init(rdev); |
/* Initialize surface registers */ |
3435,10 → 4871,6 |
if (r) |
return r; |
r = radeon_irq_kms_init(rdev); |
if (r) |
return r; |
rdev->ring[RADEON_RING_TYPE_GFX_INDEX].ring_obj = NULL; |
r600_ring_init(rdev, &rdev->ring[RADEON_RING_TYPE_GFX_INDEX], 1024 * 1024); |
3445,6 → 4877,13 |
rdev->ring[R600_RING_TYPE_DMA_INDEX].ring_obj = NULL; |
r600_ring_init(rdev, &rdev->ring[R600_RING_TYPE_DMA_INDEX], 64 * 1024); |
// r = radeon_uvd_init(rdev); |
// if (!r) { |
// rdev->ring[R600_RING_TYPE_UVD_INDEX].ring_obj = NULL; |
// r600_ring_init(rdev, &rdev->ring[R600_RING_TYPE_UVD_INDEX], |
// 4096); |
// } |
rdev->ih.ring_obj = NULL; |
r600_ih_ring_init(rdev, 64 * 1024); |
3476,8 → 4915,7 |
void evergreen_pcie_gen2_enable(struct radeon_device *rdev) |
{ |
u32 link_width_cntl, speed_cntl, mask; |
int ret; |
u32 link_width_cntl, speed_cntl; |
if (radeon_pcie_gen2 == 0) |
return; |
3492,14 → 4930,11 |
if (ASIC_IS_X2(rdev)) |
return; |
ret = drm_pcie_get_speed_cap_mask(rdev->ddev, &mask); |
if (ret != 0) |
if ((rdev->pdev->bus->max_bus_speed != PCIE_SPEED_5_0GT) && |
(rdev->pdev->bus->max_bus_speed != PCIE_SPEED_8_0GT)) |
return; |
if (!(mask & DRM_PCIE_SPEED_50)) |
return; |
speed_cntl = RREG32_PCIE_P(PCIE_LC_SPEED_CNTL); |
speed_cntl = RREG32_PCIE_PORT(PCIE_LC_SPEED_CNTL); |
if (speed_cntl & LC_CURRENT_DATA_RATE) { |
DRM_INFO("PCIE gen 2 link speeds already enabled\n"); |
return; |
3510,33 → 4945,33 |
if ((speed_cntl & LC_OTHER_SIDE_EVER_SENT_GEN2) || |
(speed_cntl & LC_OTHER_SIDE_SUPPORTS_GEN2)) { |
link_width_cntl = RREG32_PCIE_P(PCIE_LC_LINK_WIDTH_CNTL); |
link_width_cntl = RREG32_PCIE_PORT(PCIE_LC_LINK_WIDTH_CNTL); |
link_width_cntl &= ~LC_UPCONFIGURE_DIS; |
WREG32_PCIE_P(PCIE_LC_LINK_WIDTH_CNTL, link_width_cntl); |
WREG32_PCIE_PORT(PCIE_LC_LINK_WIDTH_CNTL, link_width_cntl); |
speed_cntl = RREG32_PCIE_P(PCIE_LC_SPEED_CNTL); |
speed_cntl = RREG32_PCIE_PORT(PCIE_LC_SPEED_CNTL); |
speed_cntl &= ~LC_TARGET_LINK_SPEED_OVERRIDE_EN; |
WREG32_PCIE_P(PCIE_LC_SPEED_CNTL, speed_cntl); |
WREG32_PCIE_PORT(PCIE_LC_SPEED_CNTL, speed_cntl); |
speed_cntl = RREG32_PCIE_P(PCIE_LC_SPEED_CNTL); |
speed_cntl = RREG32_PCIE_PORT(PCIE_LC_SPEED_CNTL); |
speed_cntl |= LC_CLR_FAILED_SPD_CHANGE_CNT; |
WREG32_PCIE_P(PCIE_LC_SPEED_CNTL, speed_cntl); |
WREG32_PCIE_PORT(PCIE_LC_SPEED_CNTL, speed_cntl); |
speed_cntl = RREG32_PCIE_P(PCIE_LC_SPEED_CNTL); |
speed_cntl = RREG32_PCIE_PORT(PCIE_LC_SPEED_CNTL); |
speed_cntl &= ~LC_CLR_FAILED_SPD_CHANGE_CNT; |
WREG32_PCIE_P(PCIE_LC_SPEED_CNTL, speed_cntl); |
WREG32_PCIE_PORT(PCIE_LC_SPEED_CNTL, speed_cntl); |
speed_cntl = RREG32_PCIE_P(PCIE_LC_SPEED_CNTL); |
speed_cntl = RREG32_PCIE_PORT(PCIE_LC_SPEED_CNTL); |
speed_cntl |= LC_GEN2_EN_STRAP; |
WREG32_PCIE_P(PCIE_LC_SPEED_CNTL, speed_cntl); |
WREG32_PCIE_PORT(PCIE_LC_SPEED_CNTL, speed_cntl); |
} else { |
link_width_cntl = RREG32_PCIE_P(PCIE_LC_LINK_WIDTH_CNTL); |
link_width_cntl = RREG32_PCIE_PORT(PCIE_LC_LINK_WIDTH_CNTL); |
/* XXX: only disable it if gen1 bridge vendor == 0x111d or 0x1106 */ |
if (1) |
link_width_cntl |= LC_UPCONFIGURE_DIS; |
else |
link_width_cntl &= ~LC_UPCONFIGURE_DIS; |
WREG32_PCIE_P(PCIE_LC_LINK_WIDTH_CNTL, link_width_cntl); |
WREG32_PCIE_PORT(PCIE_LC_LINK_WIDTH_CNTL, link_width_cntl); |
} |
} |
/drivers/video/drm/radeon/evergreen_blit_kms.c |
---|
724,7 → 724,7 |
radeon_bo_kunmap(rdev->r600_blit.shader_obj); |
radeon_bo_unreserve(rdev->r600_blit.shader_obj); |
// radeon_ttm_set_active_vram_size(rdev, rdev->mc.real_vram_size); |
radeon_ttm_set_active_vram_size(rdev, rdev->mc.real_vram_size); |
#endif |
/drivers/video/drm/radeon/evergreen_hdmi.c |
---|
24,6 → 24,7 |
* Authors: Christian König |
* Rafał Miłecki |
*/ |
#include <linux/hdmi.h> |
#include <drm/drmP.h> |
#include <drm/radeon_drm.h> |
#include "radeon.h" |
53,44 → 54,73 |
WREG32(HDMI_ACR_48_1 + offset, acr.n_48khz); |
} |
/* |
* calculate the crc for a given info frame |
*/ |
static void evergreen_hdmi_infoframe_checksum(uint8_t packetType, |
uint8_t versionNumber, |
uint8_t length, |
uint8_t *frame) |
static void evergreen_hdmi_write_sad_regs(struct drm_encoder *encoder) |
{ |
int i; |
frame[0] = packetType + versionNumber + length; |
for (i = 1; i <= length; i++) |
frame[0] += frame[i]; |
frame[0] = 0x100 - frame[0]; |
struct radeon_device *rdev = encoder->dev->dev_private; |
struct drm_connector *connector; |
struct radeon_connector *radeon_connector = NULL; |
struct cea_sad *sads; |
int i, sad_count; |
static const u16 eld_reg_to_type[][2] = { |
{ AZ_F0_CODEC_PIN0_CONTROL_AUDIO_DESCRIPTOR0, HDMI_AUDIO_CODING_TYPE_PCM }, |
{ AZ_F0_CODEC_PIN0_CONTROL_AUDIO_DESCRIPTOR1, HDMI_AUDIO_CODING_TYPE_AC3 }, |
{ AZ_F0_CODEC_PIN0_CONTROL_AUDIO_DESCRIPTOR2, HDMI_AUDIO_CODING_TYPE_MPEG1 }, |
{ AZ_F0_CODEC_PIN0_CONTROL_AUDIO_DESCRIPTOR3, HDMI_AUDIO_CODING_TYPE_MP3 }, |
{ AZ_F0_CODEC_PIN0_CONTROL_AUDIO_DESCRIPTOR4, HDMI_AUDIO_CODING_TYPE_MPEG2 }, |
{ AZ_F0_CODEC_PIN0_CONTROL_AUDIO_DESCRIPTOR5, HDMI_AUDIO_CODING_TYPE_AAC_LC }, |
{ AZ_F0_CODEC_PIN0_CONTROL_AUDIO_DESCRIPTOR6, HDMI_AUDIO_CODING_TYPE_DTS }, |
{ AZ_F0_CODEC_PIN0_CONTROL_AUDIO_DESCRIPTOR7, HDMI_AUDIO_CODING_TYPE_ATRAC }, |
{ AZ_F0_CODEC_PIN0_CONTROL_AUDIO_DESCRIPTOR9, HDMI_AUDIO_CODING_TYPE_EAC3 }, |
{ AZ_F0_CODEC_PIN0_CONTROL_AUDIO_DESCRIPTOR10, HDMI_AUDIO_CODING_TYPE_DTS_HD }, |
{ AZ_F0_CODEC_PIN0_CONTROL_AUDIO_DESCRIPTOR11, HDMI_AUDIO_CODING_TYPE_MLP }, |
{ AZ_F0_CODEC_PIN0_CONTROL_AUDIO_DESCRIPTOR13, HDMI_AUDIO_CODING_TYPE_WMA_PRO }, |
}; |
list_for_each_entry(connector, &encoder->dev->mode_config.connector_list, head) { |
if (connector->encoder == encoder) |
radeon_connector = to_radeon_connector(connector); |
} |
if (!radeon_connector) { |
DRM_ERROR("Couldn't find encoder's connector\n"); |
return; |
} |
sad_count = drm_edid_to_sad(radeon_connector->edid, &sads); |
if (sad_count < 0) { |
DRM_ERROR("Couldn't read SADs: %d\n", sad_count); |
return; |
} |
BUG_ON(!sads); |
for (i = 0; i < ARRAY_SIZE(eld_reg_to_type); i++) { |
u32 value = 0; |
int j; |
for (j = 0; j < sad_count; j++) { |
struct cea_sad *sad = &sads[j]; |
if (sad->format == eld_reg_to_type[i][1]) { |
value = MAX_CHANNELS(sad->channels) | |
DESCRIPTOR_BYTE_2(sad->byte2) | |
SUPPORTED_FREQUENCIES(sad->freq); |
if (sad->format == HDMI_AUDIO_CODING_TYPE_PCM) |
value |= SUPPORTED_FREQUENCIES_STEREO(sad->freq); |
break; |
} |
} |
WREG32(eld_reg_to_type[i][0], value); |
} |
kfree(sads); |
} |
/* |
* build a HDMI Video Info Frame |
*/ |
static void evergreen_hdmi_videoinfoframe( |
struct drm_encoder *encoder, |
uint8_t color_format, |
int active_information_present, |
uint8_t active_format_aspect_ratio, |
uint8_t scan_information, |
uint8_t colorimetry, |
uint8_t ex_colorimetry, |
uint8_t quantization, |
int ITC, |
uint8_t picture_aspect_ratio, |
uint8_t video_format_identification, |
uint8_t pixel_repetition, |
uint8_t non_uniform_picture_scaling, |
uint8_t bar_info_data_valid, |
uint16_t top_bar, |
uint16_t bottom_bar, |
uint16_t left_bar, |
uint16_t right_bar |
) |
static void evergreen_hdmi_update_avi_infoframe(struct drm_encoder *encoder, |
void *buffer, size_t size) |
{ |
struct drm_device *dev = encoder->dev; |
struct radeon_device *rdev = dev->dev_private; |
97,36 → 127,8 |
struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder); |
struct radeon_encoder_atom_dig *dig = radeon_encoder->enc_priv; |
uint32_t offset = dig->afmt->offset; |
uint8_t *frame = buffer + 3; |
uint8_t frame[14]; |
frame[0x0] = 0; |
frame[0x1] = |
(scan_information & 0x3) | |
((bar_info_data_valid & 0x3) << 2) | |
((active_information_present & 0x1) << 4) | |
((color_format & 0x3) << 5); |
frame[0x2] = |
(active_format_aspect_ratio & 0xF) | |
((picture_aspect_ratio & 0x3) << 4) | |
((colorimetry & 0x3) << 6); |
frame[0x3] = |
(non_uniform_picture_scaling & 0x3) | |
((quantization & 0x3) << 2) | |
((ex_colorimetry & 0x7) << 4) | |
((ITC & 0x1) << 7); |
frame[0x4] = (video_format_identification & 0x7F); |
frame[0x5] = (pixel_repetition & 0xF); |
frame[0x6] = (top_bar & 0xFF); |
frame[0x7] = (top_bar >> 8); |
frame[0x8] = (bottom_bar & 0xFF); |
frame[0x9] = (bottom_bar >> 8); |
frame[0xA] = (left_bar & 0xFF); |
frame[0xB] = (left_bar >> 8); |
frame[0xC] = (right_bar & 0xFF); |
frame[0xD] = (right_bar >> 8); |
evergreen_hdmi_infoframe_checksum(0x82, 0x02, 0x0D, frame); |
/* Our header values (type, version, length) should be alright, Intel |
* is using the same. Checksum function also seems to be OK, it works |
* fine for audio infoframe. However calculated value is always lower |
154,7 → 156,10 |
struct radeon_device *rdev = dev->dev_private; |
struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder); |
struct radeon_encoder_atom_dig *dig = radeon_encoder->enc_priv; |
u8 buffer[HDMI_INFOFRAME_HEADER_SIZE + HDMI_AVI_INFOFRAME_SIZE]; |
struct hdmi_avi_infoframe frame; |
uint32_t offset; |
ssize_t err; |
/* Silent, r600_hdmi_enable will raise WARN for us */ |
if (!dig->afmt->enabled) |
200,9 → 205,19 |
WREG32(HDMI_GC + offset, 0); /* unset HDMI_GC_AVMUTE */ |
evergreen_hdmi_videoinfoframe(encoder, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, |
0, 0, 0, 0, 0, 0); |
err = drm_hdmi_avi_infoframe_from_display_mode(&frame, mode); |
if (err < 0) { |
DRM_ERROR("failed to setup AVI infoframe: %zd\n", err); |
return; |
} |
err = hdmi_avi_infoframe_pack(&frame, buffer, sizeof(buffer)); |
if (err < 0) { |
DRM_ERROR("failed to pack AVI infoframe: %zd\n", err); |
return; |
} |
evergreen_hdmi_update_avi_infoframe(encoder, buffer, sizeof(buffer)); |
evergreen_hdmi_update_ACR(encoder, mode->clock); |
/* it's unknown what these bits do excatly, but it's indeed quite useful for debugging */ |
/drivers/video/drm/radeon/evergreen_reg.h |
---|
223,8 → 223,11 |
#define EVERGREEN_CRTC_STATUS 0x6e8c |
# define EVERGREEN_CRTC_V_BLANK (1 << 0) |
#define EVERGREEN_CRTC_STATUS_POSITION 0x6e90 |
#define EVERGREEN_CRTC_STATUS_HV_COUNT 0x6ea0 |
#define EVERGREEN_MASTER_UPDATE_MODE 0x6ef8 |
#define EVERGREEN_CRTC_UPDATE_LOCK 0x6ed4 |
#define EVERGREEN_MASTER_UPDATE_LOCK 0x6ef4 |
#define EVERGREEN_MASTER_UPDATE_MODE 0x6ef8 |
#define EVERGREEN_DC_GPIO_HPD_MASK 0x64b0 |
#define EVERGREEN_DC_GPIO_HPD_A 0x64b4 |
/drivers/video/drm/radeon/evergreend.h |
---|
53,6 → 53,43 |
#define RCU_IND_INDEX 0x100 |
#define RCU_IND_DATA 0x104 |
/* discrete uvd clocks */ |
#define CG_UPLL_FUNC_CNTL 0x718 |
# define UPLL_RESET_MASK 0x00000001 |
# define UPLL_SLEEP_MASK 0x00000002 |
# define UPLL_BYPASS_EN_MASK 0x00000004 |
# define UPLL_CTLREQ_MASK 0x00000008 |
# define UPLL_REF_DIV_MASK 0x003F0000 |
# define UPLL_VCO_MODE_MASK 0x00000200 |
# define UPLL_CTLACK_MASK 0x40000000 |
# define UPLL_CTLACK2_MASK 0x80000000 |
#define CG_UPLL_FUNC_CNTL_2 0x71c |
# define UPLL_PDIV_A(x) ((x) << 0) |
# define UPLL_PDIV_A_MASK 0x0000007F |
# define UPLL_PDIV_B(x) ((x) << 8) |
# define UPLL_PDIV_B_MASK 0x00007F00 |
# define VCLK_SRC_SEL(x) ((x) << 20) |
# define VCLK_SRC_SEL_MASK 0x01F00000 |
# define DCLK_SRC_SEL(x) ((x) << 25) |
# define DCLK_SRC_SEL_MASK 0x3E000000 |
#define CG_UPLL_FUNC_CNTL_3 0x720 |
# define UPLL_FB_DIV(x) ((x) << 0) |
# define UPLL_FB_DIV_MASK 0x01FFFFFF |
#define CG_UPLL_FUNC_CNTL_4 0x854 |
# define UPLL_SPARE_ISPARE9 0x00020000 |
#define CG_UPLL_SPREAD_SPECTRUM 0x79c |
# define SSEN_MASK 0x00000001 |
/* fusion uvd clocks */ |
#define CG_DCLK_CNTL 0x610 |
# define DCLK_DIVIDER_MASK 0x7f |
# define DCLK_DIR_CNTL_EN (1 << 8) |
#define CG_DCLK_STATUS 0x614 |
# define DCLK_STATUS (1 << 0) |
#define CG_VCLK_CNTL 0x618 |
#define CG_VCLK_STATUS 0x61c |
#define CG_SCRATCH1 0x820 |
#define GRBM_GFX_INDEX 0x802C |
#define INSTANCE_INDEX(x) ((x) << 0) |
#define SE_INDEX(x) ((x) << 16) |
197,6 → 234,7 |
# define HDMI_MPEG_INFO_CONT (1 << 9) |
#define HDMI_INFOFRAME_CONTROL1 0x7048 |
# define HDMI_AVI_INFO_LINE(x) (((x) & 0x3f) << 0) |
# define HDMI_AVI_INFO_LINE_MASK (0x3f << 0) |
# define HDMI_AUDIO_INFO_LINE(x) (((x) & 0x3f) << 8) |
# define HDMI_MPEG_INFO_LINE(x) (((x) & 0x3f) << 16) |
#define HDMI_GENERIC_PACKET_CONTROL 0x704c |
729,6 → 767,18 |
#define WAIT_UNTIL 0x8040 |
#define SRBM_STATUS 0x0E50 |
#define RLC_RQ_PENDING (1 << 3) |
#define GRBM_RQ_PENDING (1 << 5) |
#define VMC_BUSY (1 << 8) |
#define MCB_BUSY (1 << 9) |
#define MCB_NON_DISPLAY_BUSY (1 << 10) |
#define MCC_BUSY (1 << 11) |
#define MCD_BUSY (1 << 12) |
#define SEM_BUSY (1 << 14) |
#define RLC_BUSY (1 << 15) |
#define IH_BUSY (1 << 17) |
#define SRBM_STATUS2 0x0EC4 |
#define DMA_BUSY (1 << 5) |
#define SRBM_SOFT_RESET 0x0E60 |
#define SRBM_SOFT_RESET_ALL_MASK 0x00FEEFA6 |
#define SOFT_RESET_BIF (1 << 1) |
924,10 → 974,13 |
#define CAYMAN_DMA1_CNTL 0xd82c |
/* async DMA packets */ |
#define DMA_PACKET(cmd, t, s, n) ((((cmd) & 0xF) << 28) | \ |
(((t) & 0x1) << 23) | \ |
(((s) & 0x1) << 22) | \ |
#define DMA_PACKET(cmd, sub_cmd, n) ((((cmd) & 0xF) << 28) | \ |
(((sub_cmd) & 0xFF) << 20) |\ |
(((n) & 0xFFFFF) << 0)) |
#define GET_DMA_CMD(h) (((h) & 0xf0000000) >> 28) |
#define GET_DMA_COUNT(h) ((h) & 0x000fffff) |
#define GET_DMA_SUB_CMD(h) (((h) & 0x0ff00000) >> 20) |
/* async DMA Packet types */ |
#define DMA_PACKET_WRITE 0x2 |
#define DMA_PACKET_COPY 0x3 |
977,19 → 1030,20 |
# define TARGET_LINK_SPEED_MASK (0xf << 0) |
# define SELECTABLE_DEEMPHASIS (1 << 6) |
/* |
* UVD |
*/ |
#define UVD_UDEC_ADDR_CONFIG 0xef4c |
#define UVD_UDEC_DB_ADDR_CONFIG 0xef50 |
#define UVD_UDEC_DBW_ADDR_CONFIG 0xef54 |
#define UVD_RBC_RB_RPTR 0xf690 |
#define UVD_RBC_RB_WPTR 0xf694 |
/* |
* PM4 |
*/ |
#define PACKET_TYPE0 0 |
#define PACKET_TYPE1 1 |
#define PACKET_TYPE2 2 |
#define PACKET_TYPE3 3 |
#define CP_PACKET_GET_TYPE(h) (((h) >> 30) & 3) |
#define CP_PACKET_GET_COUNT(h) (((h) >> 16) & 0x3FFF) |
#define CP_PACKET0_GET_REG(h) (((h) & 0xFFFF) << 2) |
#define CP_PACKET3_GET_OPCODE(h) (((h) >> 8) & 0xFF) |
#define PACKET0(reg, n) ((PACKET_TYPE0 << 30) | \ |
#define PACKET0(reg, n) ((RADEON_PACKET_TYPE0 << 30) | \ |
(((reg) >> 2) & 0xFFFF) | \ |
((n) & 0x3FFF) << 16) |
#define CP_PACKET2 0x80000000 |
998,7 → 1052,7 |
#define PACKET2(v) (CP_PACKET2 | REG_SET(PACKET2_PAD, (v))) |
#define PACKET3(op, n) ((PACKET_TYPE3 << 30) | \ |
#define PACKET3(op, n) ((RADEON_PACKET_TYPE3 << 30) | \ |
(((op) & 0xFF) << 8) | \ |
((n) & 0x3FFF) << 16) |
/drivers/video/drm/radeon/firmware/ARUBA_me.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/ARUBA_pfp.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/ARUBA_rlc.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/BARTS_smc.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/BONAIRE_ce.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/BONAIRE_mc.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/BONAIRE_me.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/BONAIRE_mec.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/BONAIRE_pfp.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/BONAIRE_rlc.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/BONAIRE_sdma.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/BONAIRE_uvd.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/BTC_rlc.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
/drivers/video/drm/radeon/firmware/CAICOS_smc.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/CAYMAN_rlc.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
/drivers/video/drm/radeon/firmware/CAYMAN_smc.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/CEDAR_rlc.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
/drivers/video/drm/radeon/firmware/CEDAR_smc.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/CYPRESS_rlc.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
/drivers/video/drm/radeon/firmware/CYPRESS_smc.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/CYPRESS_uvd.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/HAINAN_ce.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/HAINAN_mc.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/HAINAN_me.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/HAINAN_pfp.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/HAINAN_rlc.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/HAINAN_smc.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/JUNIPER_rlc.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
/drivers/video/drm/radeon/firmware/JUNIPER_smc.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/KABINI_ce.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/KABINI_me.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/KABINI_mec.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/KABINI_pfp.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/KABINI_rlc.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/KABINI_sdma.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/OLAND_ce.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/OLAND_mc.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/OLAND_me.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/OLAND_pfp.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/OLAND_rlc.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/OLAND_smc.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/PITCAIRN_rlc.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
/drivers/video/drm/radeon/firmware/PITCAIRN_smc.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/R700_rlc.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
/drivers/video/drm/radeon/firmware/REDWOOD_rlc.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
/drivers/video/drm/radeon/firmware/REDWOOD_smc.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/RV710_smc.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/RV710_uvd.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/RV730_smc.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/RV740_smc.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/RV770_smc.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/SUMO_rlc.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
/drivers/video/drm/radeon/firmware/SUMO_uvd.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/TAHITI_rlc.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
/drivers/video/drm/radeon/firmware/TAHITI_smc.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/TAHITI_uvd.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/TURKS_smc.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/firmware/VERDE_rlc.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
/drivers/video/drm/radeon/firmware/VERDE_smc.bin |
---|
Cannot display: file marked as a binary type. |
svn:mime-type = application/octet-stream |
Property changes: |
Added: svn:mime-type |
+application/octet-stream |
\ No newline at end of property |
/drivers/video/drm/radeon/fwblob.asm |
---|
259,7 → 259,7 |
} |
SI_code TAHITI, PITCAIRN, VERDE |
SI_code TAHITI, PITCAIRN, VERDE, OLAND, HAINAN |
___end_builtin_fw: |
380,7 → 380,7 |
} |
SI_firmware TAHITI,PITCAIRN,VERDE |
SI_firmware TAHITI, PITCAIRN, VERDE, OLAND, HAINAN |
align 16 |
R100CP_START: |
/drivers/video/drm/radeon/ni.c |
---|
34,6 → 34,8 |
#include "ni_reg.h" |
#include "cayman_blit_shaders.h" |
extern bool evergreen_is_display_hung(struct radeon_device *rdev); |
extern void evergreen_print_gpu_status_regs(struct radeon_device *rdev); |
extern void evergreen_mc_stop(struct radeon_device *rdev, struct evergreen_mc_save *save); |
extern void evergreen_mc_resume(struct radeon_device *rdev, struct evergreen_mc_save *save); |
extern int evergreen_mc_wait_for_idle(struct radeon_device *rdev); |
76,6 → 78,282 |
MODULE_FIRMWARE("radeon/ARUBA_me.bin"); |
MODULE_FIRMWARE("radeon/ARUBA_rlc.bin"); |
static const u32 cayman_golden_registers2[] = |
{ |
0x3e5c, 0xffffffff, 0x00000000, |
0x3e48, 0xffffffff, 0x00000000, |
0x3e4c, 0xffffffff, 0x00000000, |
0x3e64, 0xffffffff, 0x00000000, |
0x3e50, 0xffffffff, 0x00000000, |
0x3e60, 0xffffffff, 0x00000000 |
}; |
static const u32 cayman_golden_registers[] = |
{ |
0x5eb4, 0xffffffff, 0x00000002, |
0x5e78, 0x8f311ff1, 0x001000f0, |
0x3f90, 0xffff0000, 0xff000000, |
0x9148, 0xffff0000, 0xff000000, |
0x3f94, 0xffff0000, 0xff000000, |
0x914c, 0xffff0000, 0xff000000, |
0xc78, 0x00000080, 0x00000080, |
0xbd4, 0x70073777, 0x00011003, |
0xd02c, 0xbfffff1f, 0x08421000, |
0xd0b8, 0x73773777, 0x02011003, |
0x5bc0, 0x00200000, 0x50100000, |
0x98f8, 0x33773777, 0x02011003, |
0x98fc, 0xffffffff, 0x76541032, |
0x7030, 0x31000311, 0x00000011, |
0x2f48, 0x33773777, 0x42010001, |
0x6b28, 0x00000010, 0x00000012, |
0x7728, 0x00000010, 0x00000012, |
0x10328, 0x00000010, 0x00000012, |
0x10f28, 0x00000010, 0x00000012, |
0x11b28, 0x00000010, 0x00000012, |
0x12728, 0x00000010, 0x00000012, |
0x240c, 0x000007ff, 0x00000000, |
0x8a14, 0xf000001f, 0x00000007, |
0x8b24, 0x3fff3fff, 0x00ff0fff, |
0x8b10, 0x0000ff0f, 0x00000000, |
0x28a4c, 0x07ffffff, 0x06000000, |
0x10c, 0x00000001, 0x00010003, |
0xa02c, 0xffffffff, 0x0000009b, |
0x913c, 0x0000010f, 0x01000100, |
0x8c04, 0xf8ff00ff, 0x40600060, |
0x28350, 0x00000f01, 0x00000000, |
0x9508, 0x3700001f, 0x00000002, |
0x960c, 0xffffffff, 0x54763210, |
0x88c4, 0x001f3ae3, 0x00000082, |
0x88d0, 0xffffffff, 0x0f40df40, |
0x88d4, 0x0000001f, 0x00000010, |
0x8974, 0xffffffff, 0x00000000 |
}; |
static const u32 dvst_golden_registers2[] = |
{ |
0x8f8, 0xffffffff, 0, |
0x8fc, 0x00380000, 0, |
0x8f8, 0xffffffff, 1, |
0x8fc, 0x0e000000, 0 |
}; |
static const u32 dvst_golden_registers[] = |
{ |
0x690, 0x3fff3fff, 0x20c00033, |
0x918c, 0x0fff0fff, 0x00010006, |
0x91a8, 0x0fff0fff, 0x00010006, |
0x9150, 0xffffdfff, 0x6e944040, |
0x917c, 0x0fff0fff, 0x00030002, |
0x9198, 0x0fff0fff, 0x00030002, |
0x915c, 0x0fff0fff, 0x00010000, |
0x3f90, 0xffff0001, 0xff000000, |
0x9178, 0x0fff0fff, 0x00070000, |
0x9194, 0x0fff0fff, 0x00070000, |
0x9148, 0xffff0001, 0xff000000, |
0x9190, 0x0fff0fff, 0x00090008, |
0x91ac, 0x0fff0fff, 0x00090008, |
0x3f94, 0xffff0000, 0xff000000, |
0x914c, 0xffff0000, 0xff000000, |
0x929c, 0x00000fff, 0x00000001, |
0x55e4, 0xff607fff, 0xfc000100, |
0x8a18, 0xff000fff, 0x00000100, |
0x8b28, 0xff000fff, 0x00000100, |
0x9144, 0xfffc0fff, 0x00000100, |
0x6ed8, 0x00010101, 0x00010000, |
0x9830, 0xffffffff, 0x00000000, |
0x9834, 0xf00fffff, 0x00000400, |
0x9838, 0xfffffffe, 0x00000000, |
0xd0c0, 0xff000fff, 0x00000100, |
0xd02c, 0xbfffff1f, 0x08421000, |
0xd0b8, 0x73773777, 0x12010001, |
0x5bb0, 0x000000f0, 0x00000070, |
0x98f8, 0x73773777, 0x12010001, |
0x98fc, 0xffffffff, 0x00000010, |
0x9b7c, 0x00ff0000, 0x00fc0000, |
0x8030, 0x00001f0f, 0x0000100a, |
0x2f48, 0x73773777, 0x12010001, |
0x2408, 0x00030000, 0x000c007f, |
0x8a14, 0xf000003f, 0x00000007, |
0x8b24, 0x3fff3fff, 0x00ff0fff, |
0x8b10, 0x0000ff0f, 0x00000000, |
0x28a4c, 0x07ffffff, 0x06000000, |
0x4d8, 0x00000fff, 0x00000100, |
0xa008, 0xffffffff, 0x00010000, |
0x913c, 0xffff03ff, 0x01000100, |
0x8c00, 0x000000ff, 0x00000003, |
0x8c04, 0xf8ff00ff, 0x40600060, |
0x8cf0, 0x1fff1fff, 0x08e00410, |
0x28350, 0x00000f01, 0x00000000, |
0x9508, 0xf700071f, 0x00000002, |
0x960c, 0xffffffff, 0x54763210, |
0x20ef8, 0x01ff01ff, 0x00000002, |
0x20e98, 0xfffffbff, 0x00200000, |
0x2015c, 0xffffffff, 0x00000f40, |
0x88c4, 0x001f3ae3, 0x00000082, |
0x8978, 0x3fffffff, 0x04050140, |
0x88d4, 0x0000001f, 0x00000010, |
0x8974, 0xffffffff, 0x00000000 |
}; |
static const u32 scrapper_golden_registers[] = |
{ |
0x690, 0x3fff3fff, 0x20c00033, |
0x918c, 0x0fff0fff, 0x00010006, |
0x918c, 0x0fff0fff, 0x00010006, |
0x91a8, 0x0fff0fff, 0x00010006, |
0x91a8, 0x0fff0fff, 0x00010006, |
0x9150, 0xffffdfff, 0x6e944040, |
0x9150, 0xffffdfff, 0x6e944040, |
0x917c, 0x0fff0fff, 0x00030002, |
0x917c, 0x0fff0fff, 0x00030002, |
0x9198, 0x0fff0fff, 0x00030002, |
0x9198, 0x0fff0fff, 0x00030002, |
0x915c, 0x0fff0fff, 0x00010000, |
0x915c, 0x0fff0fff, 0x00010000, |
0x3f90, 0xffff0001, 0xff000000, |
0x3f90, 0xffff0001, 0xff000000, |
0x9178, 0x0fff0fff, 0x00070000, |
0x9178, 0x0fff0fff, 0x00070000, |
0x9194, 0x0fff0fff, 0x00070000, |
0x9194, 0x0fff0fff, 0x00070000, |
0x9148, 0xffff0001, 0xff000000, |
0x9148, 0xffff0001, 0xff000000, |
0x9190, 0x0fff0fff, 0x00090008, |
0x9190, 0x0fff0fff, 0x00090008, |
0x91ac, 0x0fff0fff, 0x00090008, |
0x91ac, 0x0fff0fff, 0x00090008, |
0x3f94, 0xffff0000, 0xff000000, |
0x3f94, 0xffff0000, 0xff000000, |
0x914c, 0xffff0000, 0xff000000, |
0x914c, 0xffff0000, 0xff000000, |
0x929c, 0x00000fff, 0x00000001, |
0x929c, 0x00000fff, 0x00000001, |
0x55e4, 0xff607fff, 0xfc000100, |
0x8a18, 0xff000fff, 0x00000100, |
0x8a18, 0xff000fff, 0x00000100, |
0x8b28, 0xff000fff, 0x00000100, |
0x8b28, 0xff000fff, 0x00000100, |
0x9144, 0xfffc0fff, 0x00000100, |
0x9144, 0xfffc0fff, 0x00000100, |
0x6ed8, 0x00010101, 0x00010000, |
0x9830, 0xffffffff, 0x00000000, |
0x9830, 0xffffffff, 0x00000000, |
0x9834, 0xf00fffff, 0x00000400, |
0x9834, 0xf00fffff, 0x00000400, |
0x9838, 0xfffffffe, 0x00000000, |
0x9838, 0xfffffffe, 0x00000000, |
0xd0c0, 0xff000fff, 0x00000100, |
0xd02c, 0xbfffff1f, 0x08421000, |
0xd02c, 0xbfffff1f, 0x08421000, |
0xd0b8, 0x73773777, 0x12010001, |
0xd0b8, 0x73773777, 0x12010001, |
0x5bb0, 0x000000f0, 0x00000070, |
0x98f8, 0x73773777, 0x12010001, |
0x98f8, 0x73773777, 0x12010001, |
0x98fc, 0xffffffff, 0x00000010, |
0x98fc, 0xffffffff, 0x00000010, |
0x9b7c, 0x00ff0000, 0x00fc0000, |
0x9b7c, 0x00ff0000, 0x00fc0000, |
0x8030, 0x00001f0f, 0x0000100a, |
0x8030, 0x00001f0f, 0x0000100a, |
0x2f48, 0x73773777, 0x12010001, |
0x2f48, 0x73773777, 0x12010001, |
0x2408, 0x00030000, 0x000c007f, |
0x8a14, 0xf000003f, 0x00000007, |
0x8a14, 0xf000003f, 0x00000007, |
0x8b24, 0x3fff3fff, 0x00ff0fff, |
0x8b24, 0x3fff3fff, 0x00ff0fff, |
0x8b10, 0x0000ff0f, 0x00000000, |
0x8b10, 0x0000ff0f, 0x00000000, |
0x28a4c, 0x07ffffff, 0x06000000, |
0x28a4c, 0x07ffffff, 0x06000000, |
0x4d8, 0x00000fff, 0x00000100, |
0x4d8, 0x00000fff, 0x00000100, |
0xa008, 0xffffffff, 0x00010000, |
0xa008, 0xffffffff, 0x00010000, |
0x913c, 0xffff03ff, 0x01000100, |
0x913c, 0xffff03ff, 0x01000100, |
0x90e8, 0x001fffff, 0x010400c0, |
0x8c00, 0x000000ff, 0x00000003, |
0x8c00, 0x000000ff, 0x00000003, |
0x8c04, 0xf8ff00ff, 0x40600060, |
0x8c04, 0xf8ff00ff, 0x40600060, |
0x8c30, 0x0000000f, 0x00040005, |
0x8cf0, 0x1fff1fff, 0x08e00410, |
0x8cf0, 0x1fff1fff, 0x08e00410, |
0x900c, 0x00ffffff, 0x0017071f, |
0x28350, 0x00000f01, 0x00000000, |
0x28350, 0x00000f01, 0x00000000, |
0x9508, 0xf700071f, 0x00000002, |
0x9508, 0xf700071f, 0x00000002, |
0x9688, 0x00300000, 0x0017000f, |
0x960c, 0xffffffff, 0x54763210, |
0x960c, 0xffffffff, 0x54763210, |
0x20ef8, 0x01ff01ff, 0x00000002, |
0x20e98, 0xfffffbff, 0x00200000, |
0x2015c, 0xffffffff, 0x00000f40, |
0x88c4, 0x001f3ae3, 0x00000082, |
0x88c4, 0x001f3ae3, 0x00000082, |
0x8978, 0x3fffffff, 0x04050140, |
0x8978, 0x3fffffff, 0x04050140, |
0x88d4, 0x0000001f, 0x00000010, |
0x88d4, 0x0000001f, 0x00000010, |
0x8974, 0xffffffff, 0x00000000, |
0x8974, 0xffffffff, 0x00000000 |
}; |
static void ni_init_golden_registers(struct radeon_device *rdev) |
{ |
switch (rdev->family) { |
case CHIP_CAYMAN: |
radeon_program_register_sequence(rdev, |
cayman_golden_registers, |
(const u32)ARRAY_SIZE(cayman_golden_registers)); |
radeon_program_register_sequence(rdev, |
cayman_golden_registers2, |
(const u32)ARRAY_SIZE(cayman_golden_registers2)); |
break; |
case CHIP_ARUBA: |
if ((rdev->pdev->device == 0x9900) || |
(rdev->pdev->device == 0x9901) || |
(rdev->pdev->device == 0x9903) || |
(rdev->pdev->device == 0x9904) || |
(rdev->pdev->device == 0x9905) || |
(rdev->pdev->device == 0x9906) || |
(rdev->pdev->device == 0x9907) || |
(rdev->pdev->device == 0x9908) || |
(rdev->pdev->device == 0x9909) || |
(rdev->pdev->device == 0x990A) || |
(rdev->pdev->device == 0x990B) || |
(rdev->pdev->device == 0x990C) || |
(rdev->pdev->device == 0x990D) || |
(rdev->pdev->device == 0x990E) || |
(rdev->pdev->device == 0x990F) || |
(rdev->pdev->device == 0x9910) || |
(rdev->pdev->device == 0x9913) || |
(rdev->pdev->device == 0x9917) || |
(rdev->pdev->device == 0x9918)) { |
radeon_program_register_sequence(rdev, |
dvst_golden_registers, |
(const u32)ARRAY_SIZE(dvst_golden_registers)); |
radeon_program_register_sequence(rdev, |
dvst_golden_registers2, |
(const u32)ARRAY_SIZE(dvst_golden_registers2)); |
} else { |
radeon_program_register_sequence(rdev, |
scrapper_golden_registers, |
(const u32)ARRAY_SIZE(scrapper_golden_registers)); |
radeon_program_register_sequence(rdev, |
dvst_golden_registers2, |
(const u32)ARRAY_SIZE(dvst_golden_registers2)); |
} |
break; |
default: |
break; |
} |
} |
#define BTC_IO_MC_REGS_SIZE 29 |
static const u32 barts_io_mc_regs[BTC_IO_MC_REGS_SIZE][2] = { |
466,15 → 744,23 |
(rdev->pdev->device == 0x9907) || |
(rdev->pdev->device == 0x9908) || |
(rdev->pdev->device == 0x9909) || |
(rdev->pdev->device == 0x990B) || |
(rdev->pdev->device == 0x990C) || |
(rdev->pdev->device == 0x990F) || |
(rdev->pdev->device == 0x9910) || |
(rdev->pdev->device == 0x9917)) { |
(rdev->pdev->device == 0x9917) || |
(rdev->pdev->device == 0x9999) || |
(rdev->pdev->device == 0x999C)) { |
rdev->config.cayman.max_simds_per_se = 6; |
rdev->config.cayman.max_backends_per_se = 2; |
} else if ((rdev->pdev->device == 0x9903) || |
(rdev->pdev->device == 0x9904) || |
(rdev->pdev->device == 0x990A) || |
(rdev->pdev->device == 0x990D) || |
(rdev->pdev->device == 0x990E) || |
(rdev->pdev->device == 0x9913) || |
(rdev->pdev->device == 0x9918)) { |
(rdev->pdev->device == 0x9918) || |
(rdev->pdev->device == 0x999D)) { |
rdev->config.cayman.max_simds_per_se = 4; |
rdev->config.cayman.max_backends_per_se = 2; |
} else if ((rdev->pdev->device == 0x9919) || |
481,6 → 767,9 |
(rdev->pdev->device == 0x9990) || |
(rdev->pdev->device == 0x9991) || |
(rdev->pdev->device == 0x9994) || |
(rdev->pdev->device == 0x9995) || |
(rdev->pdev->device == 0x9996) || |
(rdev->pdev->device == 0x999A) || |
(rdev->pdev->device == 0x99A0)) { |
rdev->config.cayman.max_simds_per_se = 3; |
rdev->config.cayman.max_backends_per_se = 1; |
604,6 → 893,14 |
} |
/* enabled rb are just the one not disabled :) */ |
disabled_rb_mask = tmp; |
tmp = 0; |
for (i = 0; i < (rdev->config.cayman.max_backends_per_se * rdev->config.cayman.max_shader_engines); i++) |
tmp |= (1 << i); |
/* if all the backends are disabled, fix it up here */ |
if ((disabled_rb_mask & tmp) == tmp) { |
for (i = 0; i < (rdev->config.cayman.max_backends_per_se * rdev->config.cayman.max_shader_engines); i++) |
disabled_rb_mask &= ~(1 << i); |
} |
WREG32(GRBM_GFX_INDEX, INSTANCE_BROADCAST_WRITES | SE_BROADCAST_WRITES); |
WREG32(RLC_GFX_INDEX, INSTANCE_BROADCAST_WRITES | SE_BROADCAST_WRITES); |
610,15 → 907,31 |
WREG32(GB_ADDR_CONFIG, gb_addr_config); |
WREG32(DMIF_ADDR_CONFIG, gb_addr_config); |
if (ASIC_IS_DCE6(rdev)) |
WREG32(DMIF_ADDR_CALC, gb_addr_config); |
WREG32(HDP_ADDR_CONFIG, gb_addr_config); |
WREG32(DMA_TILING_CONFIG + DMA0_REGISTER_OFFSET, gb_addr_config); |
WREG32(DMA_TILING_CONFIG + DMA1_REGISTER_OFFSET, gb_addr_config); |
WREG32(UVD_UDEC_ADDR_CONFIG, gb_addr_config); |
WREG32(UVD_UDEC_DB_ADDR_CONFIG, gb_addr_config); |
WREG32(UVD_UDEC_DBW_ADDR_CONFIG, gb_addr_config); |
if ((rdev->config.cayman.max_backends_per_se == 1) && |
(rdev->flags & RADEON_IS_IGP)) { |
if ((disabled_rb_mask & 3) == 1) { |
/* RB0 disabled, RB1 enabled */ |
tmp = 0x11111111; |
} else { |
/* RB1 disabled, RB0 enabled */ |
tmp = 0x00000000; |
} |
} else { |
tmp = gb_addr_config & NUM_PIPES_MASK; |
tmp = r6xx_remap_render_backend(rdev, tmp, |
rdev->config.cayman.max_backends_per_se * |
rdev->config.cayman.max_shader_engines, |
CAYMAN_MAX_BACKENDS, disabled_rb_mask); |
} |
WREG32(GB_BACKEND_MAP, tmp); |
cgts_tcc_disable = 0xffff0000; |
902,6 → 1215,23 |
radeon_ring_write(ring, 10); /* poll interval */ |
} |
void cayman_uvd_semaphore_emit(struct radeon_device *rdev, |
struct radeon_ring *ring, |
struct radeon_semaphore *semaphore, |
bool emit_wait) |
{ |
uint64_t addr = semaphore->gpu_addr; |
radeon_ring_write(ring, PACKET0(UVD_SEMA_ADDR_LOW, 0)); |
radeon_ring_write(ring, (addr >> 3) & 0x000FFFFF); |
radeon_ring_write(ring, PACKET0(UVD_SEMA_ADDR_HIGH, 0)); |
radeon_ring_write(ring, (addr >> 23) & 0x000FFFFF); |
radeon_ring_write(ring, PACKET0(UVD_SEMA_CMD, 0)); |
radeon_ring_write(ring, 0x80 | (emit_wait ? 1 : 0)); |
} |
static void cayman_cp_enable(struct radeon_device *rdev, bool enable) |
{ |
if (enable) |
1202,7 → 1532,7 |
int cayman_dma_resume(struct radeon_device *rdev) |
{ |
struct radeon_ring *ring; |
u32 rb_cntl, dma_cntl; |
u32 rb_cntl, dma_cntl, ib_cntl; |
u32 rb_bufsz; |
u32 reg_offset, wb_offset; |
int i, r; |
1251,7 → 1581,11 |
WREG32(DMA_RB_BASE + reg_offset, ring->gpu_addr >> 8); |
/* enable DMA IBs */ |
WREG32(DMA_IB_CNTL + reg_offset, DMA_IB_ENABLE | CMD_VMID_FORCE); |
ib_cntl = DMA_IB_ENABLE | CMD_VMID_FORCE; |
#ifdef __BIG_ENDIAN |
ib_cntl |= DMA_IB_SWAP_ENABLE; |
#endif |
WREG32(DMA_IB_CNTL + reg_offset, ib_cntl); |
dma_cntl = RREG32(DMA_CNTL + reg_offset); |
dma_cntl &= ~CTXEMPTY_INT_ENABLE; |
1292,114 → 1626,96 |
radeon_ring_fini(rdev, &rdev->ring[CAYMAN_RING_TYPE_DMA1_INDEX]); |
} |
static void cayman_gpu_soft_reset_gfx(struct radeon_device *rdev) |
static u32 cayman_gpu_check_soft_reset(struct radeon_device *rdev) |
{ |
u32 grbm_reset = 0; |
u32 reset_mask = 0; |
u32 tmp; |
if (!(RREG32(GRBM_STATUS) & GUI_ACTIVE)) |
return; |
/* GRBM_STATUS */ |
tmp = RREG32(GRBM_STATUS); |
if (tmp & (PA_BUSY | SC_BUSY | |
SH_BUSY | SX_BUSY | |
TA_BUSY | VGT_BUSY | |
DB_BUSY | CB_BUSY | |
GDS_BUSY | SPI_BUSY | |
IA_BUSY | IA_BUSY_NO_DMA)) |
reset_mask |= RADEON_RESET_GFX; |
dev_info(rdev->dev, " GRBM_STATUS = 0x%08X\n", |
RREG32(GRBM_STATUS)); |
dev_info(rdev->dev, " GRBM_STATUS_SE0 = 0x%08X\n", |
RREG32(GRBM_STATUS_SE0)); |
dev_info(rdev->dev, " GRBM_STATUS_SE1 = 0x%08X\n", |
RREG32(GRBM_STATUS_SE1)); |
dev_info(rdev->dev, " SRBM_STATUS = 0x%08X\n", |
RREG32(SRBM_STATUS)); |
dev_info(rdev->dev, " R_008674_CP_STALLED_STAT1 = 0x%08X\n", |
RREG32(CP_STALLED_STAT1)); |
dev_info(rdev->dev, " R_008678_CP_STALLED_STAT2 = 0x%08X\n", |
RREG32(CP_STALLED_STAT2)); |
dev_info(rdev->dev, " R_00867C_CP_BUSY_STAT = 0x%08X\n", |
RREG32(CP_BUSY_STAT)); |
dev_info(rdev->dev, " R_008680_CP_STAT = 0x%08X\n", |
RREG32(CP_STAT)); |
if (tmp & (CF_RQ_PENDING | PF_RQ_PENDING | |
CP_BUSY | CP_COHERENCY_BUSY)) |
reset_mask |= RADEON_RESET_CP; |
/* Disable CP parsing/prefetching */ |
WREG32(CP_ME_CNTL, CP_ME_HALT | CP_PFP_HALT); |
if (tmp & GRBM_EE_BUSY) |
reset_mask |= RADEON_RESET_GRBM | RADEON_RESET_GFX | RADEON_RESET_CP; |
/* reset all the gfx blocks */ |
grbm_reset = (SOFT_RESET_CP | |
SOFT_RESET_CB | |
SOFT_RESET_DB | |
SOFT_RESET_GDS | |
SOFT_RESET_PA | |
SOFT_RESET_SC | |
SOFT_RESET_SPI | |
SOFT_RESET_SH | |
SOFT_RESET_SX | |
SOFT_RESET_TC | |
SOFT_RESET_TA | |
SOFT_RESET_VGT | |
SOFT_RESET_IA); |
/* DMA_STATUS_REG 0 */ |
tmp = RREG32(DMA_STATUS_REG + DMA0_REGISTER_OFFSET); |
if (!(tmp & DMA_IDLE)) |
reset_mask |= RADEON_RESET_DMA; |
dev_info(rdev->dev, " GRBM_SOFT_RESET=0x%08X\n", grbm_reset); |
WREG32(GRBM_SOFT_RESET, grbm_reset); |
(void)RREG32(GRBM_SOFT_RESET); |
udelay(50); |
WREG32(GRBM_SOFT_RESET, 0); |
(void)RREG32(GRBM_SOFT_RESET); |
/* DMA_STATUS_REG 1 */ |
tmp = RREG32(DMA_STATUS_REG + DMA1_REGISTER_OFFSET); |
if (!(tmp & DMA_IDLE)) |
reset_mask |= RADEON_RESET_DMA1; |
dev_info(rdev->dev, " GRBM_STATUS = 0x%08X\n", |
RREG32(GRBM_STATUS)); |
dev_info(rdev->dev, " GRBM_STATUS_SE0 = 0x%08X\n", |
RREG32(GRBM_STATUS_SE0)); |
dev_info(rdev->dev, " GRBM_STATUS_SE1 = 0x%08X\n", |
RREG32(GRBM_STATUS_SE1)); |
dev_info(rdev->dev, " SRBM_STATUS = 0x%08X\n", |
RREG32(SRBM_STATUS)); |
dev_info(rdev->dev, " R_008674_CP_STALLED_STAT1 = 0x%08X\n", |
RREG32(CP_STALLED_STAT1)); |
dev_info(rdev->dev, " R_008678_CP_STALLED_STAT2 = 0x%08X\n", |
RREG32(CP_STALLED_STAT2)); |
dev_info(rdev->dev, " R_00867C_CP_BUSY_STAT = 0x%08X\n", |
RREG32(CP_BUSY_STAT)); |
dev_info(rdev->dev, " R_008680_CP_STAT = 0x%08X\n", |
RREG32(CP_STAT)); |
/* SRBM_STATUS2 */ |
tmp = RREG32(SRBM_STATUS2); |
if (tmp & DMA_BUSY) |
reset_mask |= RADEON_RESET_DMA; |
} |
if (tmp & DMA1_BUSY) |
reset_mask |= RADEON_RESET_DMA1; |
static void cayman_gpu_soft_reset_dma(struct radeon_device *rdev) |
{ |
u32 tmp; |
/* SRBM_STATUS */ |
tmp = RREG32(SRBM_STATUS); |
if (tmp & (RLC_RQ_PENDING | RLC_BUSY)) |
reset_mask |= RADEON_RESET_RLC; |
if (RREG32(DMA_STATUS_REG) & DMA_IDLE) |
return; |
if (tmp & IH_BUSY) |
reset_mask |= RADEON_RESET_IH; |
dev_info(rdev->dev, " R_00D034_DMA_STATUS_REG = 0x%08X\n", |
RREG32(DMA_STATUS_REG)); |
if (tmp & SEM_BUSY) |
reset_mask |= RADEON_RESET_SEM; |
/* dma0 */ |
tmp = RREG32(DMA_RB_CNTL + DMA0_REGISTER_OFFSET); |
tmp &= ~DMA_RB_ENABLE; |
WREG32(DMA_RB_CNTL + DMA0_REGISTER_OFFSET, tmp); |
if (tmp & GRBM_RQ_PENDING) |
reset_mask |= RADEON_RESET_GRBM; |
/* dma1 */ |
tmp = RREG32(DMA_RB_CNTL + DMA1_REGISTER_OFFSET); |
tmp &= ~DMA_RB_ENABLE; |
WREG32(DMA_RB_CNTL + DMA1_REGISTER_OFFSET, tmp); |
if (tmp & VMC_BUSY) |
reset_mask |= RADEON_RESET_VMC; |
/* Reset dma */ |
WREG32(SRBM_SOFT_RESET, SOFT_RESET_DMA | SOFT_RESET_DMA1); |
RREG32(SRBM_SOFT_RESET); |
udelay(50); |
WREG32(SRBM_SOFT_RESET, 0); |
if (tmp & (MCB_BUSY | MCB_NON_DISPLAY_BUSY | |
MCC_BUSY | MCD_BUSY)) |
reset_mask |= RADEON_RESET_MC; |
dev_info(rdev->dev, " R_00D034_DMA_STATUS_REG = 0x%08X\n", |
RREG32(DMA_STATUS_REG)); |
if (evergreen_is_display_hung(rdev)) |
reset_mask |= RADEON_RESET_DISPLAY; |
/* VM_L2_STATUS */ |
tmp = RREG32(VM_L2_STATUS); |
if (tmp & L2_BUSY) |
reset_mask |= RADEON_RESET_VMC; |
/* Skip MC reset as it's mostly likely not hung, just busy */ |
if (reset_mask & RADEON_RESET_MC) { |
DRM_DEBUG("MC busy: 0x%08X, clearing.\n", reset_mask); |
reset_mask &= ~RADEON_RESET_MC; |
} |
static int cayman_gpu_soft_reset(struct radeon_device *rdev, u32 reset_mask) |
return reset_mask; |
} |
static void cayman_gpu_soft_reset(struct radeon_device *rdev, u32 reset_mask) |
{ |
struct evergreen_mc_save save; |
u32 grbm_soft_reset = 0, srbm_soft_reset = 0; |
u32 tmp; |
if (reset_mask == 0) |
return 0; |
return; |
dev_info(rdev->dev, "GPU softreset: 0x%08X\n", reset_mask); |
evergreen_print_gpu_status_regs(rdev); |
dev_info(rdev->dev, " VM_CONTEXT0_PROTECTION_FAULT_ADDR 0x%08X\n", |
RREG32(0x14F8)); |
dev_info(rdev->dev, " VM_CONTEXT0_PROTECTION_FAULT_STATUS 0x%08X\n", |
1409,30 → 1725,159 |
dev_info(rdev->dev, " VM_CONTEXT1_PROTECTION_FAULT_STATUS 0x%08X\n", |
RREG32(0x14DC)); |
/* Disable CP parsing/prefetching */ |
WREG32(CP_ME_CNTL, CP_ME_HALT | CP_PFP_HALT); |
if (reset_mask & RADEON_RESET_DMA) { |
/* dma0 */ |
tmp = RREG32(DMA_RB_CNTL + DMA0_REGISTER_OFFSET); |
tmp &= ~DMA_RB_ENABLE; |
WREG32(DMA_RB_CNTL + DMA0_REGISTER_OFFSET, tmp); |
} |
if (reset_mask & RADEON_RESET_DMA1) { |
/* dma1 */ |
tmp = RREG32(DMA_RB_CNTL + DMA1_REGISTER_OFFSET); |
tmp &= ~DMA_RB_ENABLE; |
WREG32(DMA_RB_CNTL + DMA1_REGISTER_OFFSET, tmp); |
} |
udelay(50); |
evergreen_mc_stop(rdev, &save); |
if (evergreen_mc_wait_for_idle(rdev)) { |
dev_warn(rdev->dev, "Wait for MC idle timedout !\n"); |
} |
if (reset_mask & (RADEON_RESET_GFX | RADEON_RESET_COMPUTE)) |
cayman_gpu_soft_reset_gfx(rdev); |
if (reset_mask & (RADEON_RESET_GFX | RADEON_RESET_COMPUTE)) { |
grbm_soft_reset = SOFT_RESET_CB | |
SOFT_RESET_DB | |
SOFT_RESET_GDS | |
SOFT_RESET_PA | |
SOFT_RESET_SC | |
SOFT_RESET_SPI | |
SOFT_RESET_SH | |
SOFT_RESET_SX | |
SOFT_RESET_TC | |
SOFT_RESET_TA | |
SOFT_RESET_VGT | |
SOFT_RESET_IA; |
} |
if (reset_mask & RADEON_RESET_CP) { |
grbm_soft_reset |= SOFT_RESET_CP | SOFT_RESET_VGT; |
srbm_soft_reset |= SOFT_RESET_GRBM; |
} |
if (reset_mask & RADEON_RESET_DMA) |
cayman_gpu_soft_reset_dma(rdev); |
srbm_soft_reset |= SOFT_RESET_DMA; |
if (reset_mask & RADEON_RESET_DMA1) |
srbm_soft_reset |= SOFT_RESET_DMA1; |
if (reset_mask & RADEON_RESET_DISPLAY) |
srbm_soft_reset |= SOFT_RESET_DC; |
if (reset_mask & RADEON_RESET_RLC) |
srbm_soft_reset |= SOFT_RESET_RLC; |
if (reset_mask & RADEON_RESET_SEM) |
srbm_soft_reset |= SOFT_RESET_SEM; |
if (reset_mask & RADEON_RESET_IH) |
srbm_soft_reset |= SOFT_RESET_IH; |
if (reset_mask & RADEON_RESET_GRBM) |
srbm_soft_reset |= SOFT_RESET_GRBM; |
if (reset_mask & RADEON_RESET_VMC) |
srbm_soft_reset |= SOFT_RESET_VMC; |
if (!(rdev->flags & RADEON_IS_IGP)) { |
if (reset_mask & RADEON_RESET_MC) |
srbm_soft_reset |= SOFT_RESET_MC; |
} |
if (grbm_soft_reset) { |
tmp = RREG32(GRBM_SOFT_RESET); |
tmp |= grbm_soft_reset; |
dev_info(rdev->dev, "GRBM_SOFT_RESET=0x%08X\n", tmp); |
WREG32(GRBM_SOFT_RESET, tmp); |
tmp = RREG32(GRBM_SOFT_RESET); |
udelay(50); |
tmp &= ~grbm_soft_reset; |
WREG32(GRBM_SOFT_RESET, tmp); |
tmp = RREG32(GRBM_SOFT_RESET); |
} |
if (srbm_soft_reset) { |
tmp = RREG32(SRBM_SOFT_RESET); |
tmp |= srbm_soft_reset; |
dev_info(rdev->dev, "SRBM_SOFT_RESET=0x%08X\n", tmp); |
WREG32(SRBM_SOFT_RESET, tmp); |
tmp = RREG32(SRBM_SOFT_RESET); |
udelay(50); |
tmp &= ~srbm_soft_reset; |
WREG32(SRBM_SOFT_RESET, tmp); |
tmp = RREG32(SRBM_SOFT_RESET); |
} |
/* Wait a little for things to settle down */ |
udelay(50); |
evergreen_mc_resume(rdev, &save); |
return 0; |
udelay(50); |
evergreen_print_gpu_status_regs(rdev); |
} |
int cayman_asic_reset(struct radeon_device *rdev) |
{ |
return cayman_gpu_soft_reset(rdev, (RADEON_RESET_GFX | |
u32 reset_mask; |
reset_mask = cayman_gpu_check_soft_reset(rdev); |
if (reset_mask) |
r600_set_bios_scratch_engine_hung(rdev, true); |
cayman_gpu_soft_reset(rdev, reset_mask); |
reset_mask = cayman_gpu_check_soft_reset(rdev); |
if (!reset_mask) |
r600_set_bios_scratch_engine_hung(rdev, false); |
return 0; |
} |
/** |
* cayman_gfx_is_lockup - Check if the GFX engine is locked up |
* |
* @rdev: radeon_device pointer |
* @ring: radeon_ring structure holding ring information |
* |
* Check if the GFX engine is locked up. |
* Returns true if the engine appears to be locked up, false if not. |
*/ |
bool cayman_gfx_is_lockup(struct radeon_device *rdev, struct radeon_ring *ring) |
{ |
u32 reset_mask = cayman_gpu_check_soft_reset(rdev); |
if (!(reset_mask & (RADEON_RESET_GFX | |
RADEON_RESET_COMPUTE | |
RADEON_RESET_DMA)); |
RADEON_RESET_CP))) { |
radeon_ring_lockup_update(ring); |
return false; |
} |
/* force CP activities */ |
radeon_ring_force_activity(rdev, ring); |
return radeon_ring_test_lockup(rdev, ring); |
} |
/** |
* cayman_dma_is_lockup - Check if the DMA engine is locked up |
1440,18 → 1885,20 |
* @rdev: radeon_device pointer |
* @ring: radeon_ring structure holding ring information |
* |
* Check if the async DMA engine is locked up (cayman-SI). |
* Check if the async DMA engine is locked up. |
* Returns true if the engine appears to be locked up, false if not. |
*/ |
bool cayman_dma_is_lockup(struct radeon_device *rdev, struct radeon_ring *ring) |
{ |
u32 dma_status_reg; |
u32 reset_mask = cayman_gpu_check_soft_reset(rdev); |
u32 mask; |
if (ring->idx == R600_RING_TYPE_DMA_INDEX) |
dma_status_reg = RREG32(DMA_STATUS_REG + DMA0_REGISTER_OFFSET); |
mask = RADEON_RESET_DMA; |
else |
dma_status_reg = RREG32(DMA_STATUS_REG + DMA1_REGISTER_OFFSET); |
if (dma_status_reg & DMA_IDLE) { |
mask = RADEON_RESET_DMA1; |
if (!(reset_mask & mask)) { |
radeon_ring_lockup_update(ring); |
return false; |
} |
1529,6 → 1976,16 |
return r; |
} |
// r = rv770_uvd_resume(rdev); |
// if (!r) { |
// r = radeon_fence_driver_start_ring(rdev, |
// R600_RING_TYPE_UVD_INDEX); |
// if (r) |
// dev_err(rdev->dev, "UVD fences init error (%d).\n", r); |
// } |
// if (r) |
// rdev->ring[R600_RING_TYPE_UVD_INDEX].ring_size = 0; |
r = radeon_fence_driver_start_ring(rdev, CAYMAN_RING_TYPE_CP1_INDEX); |
if (r) { |
dev_err(rdev->dev, "failed initializing CP fences (%d).\n", r); |
1554,6 → 2011,12 |
} |
/* Enable IRQ */ |
if (!rdev->irq.installed) { |
r = radeon_irq_kms_init(rdev); |
if (r) |
return r; |
} |
r = r600_irq_init(rdev); |
if (r) { |
DRM_ERROR("radeon: IH init failed (%d).\n", r); |
1595,11 → 2058,31 |
if (r) |
return r; |
ring = &rdev->ring[R600_RING_TYPE_UVD_INDEX]; |
if (ring->ring_size) { |
r = radeon_ring_init(rdev, ring, ring->ring_size, |
R600_WB_UVD_RPTR_OFFSET, |
UVD_RBC_RB_RPTR, UVD_RBC_RB_WPTR, |
0, 0xfffff, RADEON_CP_PACKET2); |
if (!r) |
r = r600_uvd_init(rdev); |
if (r) |
DRM_ERROR("radeon: failed initializing UVD (%d).\n", r); |
} |
r = radeon_ib_pool_init(rdev); |
if (r) { |
dev_err(rdev->dev, "IB initialization failed (%d).\n", r); |
return r; |
} |
r = radeon_vm_manager_init(rdev); |
if (r) { |
dev_err(rdev->dev, "vm manager initialization failed (%d).\n", r); |
return r; |
} |
return 0; |
} |
1641,6 → 2124,8 |
DRM_INFO("GPU not posted. posting now...\n"); |
atom_asic_init(rdev->mode_info.atom_context); |
} |
/* init golden registers */ |
ni_init_golden_registers(rdev); |
/* Initialize scratch registers */ |
r600_scratch_init(rdev); |
/* Initialize surface registers */ |
1660,10 → 2145,6 |
if (r) |
return r; |
r = radeon_irq_kms_init(rdev); |
if (r) |
return r; |
ring->ring_obj = NULL; |
r600_ring_init(rdev, ring, 1024 * 1024); |
1675,6 → 2156,13 |
ring->ring_obj = NULL; |
r600_ring_init(rdev, ring, 64 * 1024); |
// r = radeon_uvd_init(rdev); |
// if (!r) { |
// ring = &rdev->ring[R600_RING_TYPE_UVD_INDEX]; |
// ring->ring_obj = NULL; |
// r600_ring_init(rdev, ring, 4096); |
// } |
rdev->ih.ring_obj = NULL; |
r600_ih_ring_init(rdev, 64 * 1024); |
1748,6 → 2236,7 |
* cayman_vm_set_page - update the page tables using the CP |
* |
* @rdev: radeon_device pointer |
* @ib: indirect buffer to fill with commands |
* @pe: addr of the page entry |
* @addr: dst addr to write into pe |
* @count: number of page entries to update |
1754,13 → 2243,14 |
* @incr: increase next addr by incr bytes |
* @flags: access flags |
* |
* Update the page tables using the CP (cayman-si). |
* Update the page tables using the CP (cayman/TN). |
*/ |
void cayman_vm_set_page(struct radeon_device *rdev, uint64_t pe, |
void cayman_vm_set_page(struct radeon_device *rdev, |
struct radeon_ib *ib, |
uint64_t pe, |
uint64_t addr, unsigned count, |
uint32_t incr, uint32_t flags) |
{ |
struct radeon_ring *ring = &rdev->ring[rdev->asic->vm.pt_ring_index]; |
uint32_t r600_flags = cayman_vm_page_flags(rdev, flags); |
uint64_t value; |
unsigned ndw; |
1771,9 → 2261,9 |
if (ndw > 0x3FFF) |
ndw = 0x3FFF; |
radeon_ring_write(ring, PACKET3(PACKET3_ME_WRITE, ndw)); |
radeon_ring_write(ring, pe); |
radeon_ring_write(ring, upper_32_bits(pe) & 0xff); |
ib->ptr[ib->length_dw++] = PACKET3(PACKET3_ME_WRITE, ndw); |
ib->ptr[ib->length_dw++] = pe; |
ib->ptr[ib->length_dw++] = upper_32_bits(pe) & 0xff; |
for (; ndw > 1; ndw -= 2, --count, pe += 8) { |
if (flags & RADEON_VM_PAGE_SYSTEM) { |
value = radeon_vm_map_gart(rdev, addr); |
1785,11 → 2275,13 |
} |
addr += incr; |
value |= r600_flags; |
radeon_ring_write(ring, value); |
radeon_ring_write(ring, upper_32_bits(value)); |
ib->ptr[ib->length_dw++] = value; |
ib->ptr[ib->length_dw++] = upper_32_bits(value); |
} |
} |
} else { |
if ((flags & RADEON_VM_PAGE_SYSTEM) || |
(count == 1)) { |
while (count) { |
ndw = count * 2; |
if (ndw > 0xFFFFE) |
1796,9 → 2288,9 |
ndw = 0xFFFFE; |
/* for non-physically contiguous pages (system) */ |
radeon_ring_write(ring, DMA_PACKET(DMA_PACKET_WRITE, 0, 0, ndw)); |
radeon_ring_write(ring, pe); |
radeon_ring_write(ring, upper_32_bits(pe) & 0xff); |
ib->ptr[ib->length_dw++] = DMA_PACKET(DMA_PACKET_WRITE, 0, 0, ndw); |
ib->ptr[ib->length_dw++] = pe; |
ib->ptr[ib->length_dw++] = upper_32_bits(pe) & 0xff; |
for (; ndw > 0; ndw -= 2, --count, pe += 8) { |
if (flags & RADEON_VM_PAGE_SYSTEM) { |
value = radeon_vm_map_gart(rdev, addr); |
1810,12 → 2302,41 |
} |
addr += incr; |
value |= r600_flags; |
radeon_ring_write(ring, value); |
radeon_ring_write(ring, upper_32_bits(value)); |
ib->ptr[ib->length_dw++] = value; |
ib->ptr[ib->length_dw++] = upper_32_bits(value); |
} |
} |
while (ib->length_dw & 0x7) |
ib->ptr[ib->length_dw++] = DMA_PACKET(DMA_PACKET_NOP, 0, 0, 0); |
} else { |
while (count) { |
ndw = count * 2; |
if (ndw > 0xFFFFE) |
ndw = 0xFFFFE; |
if (flags & RADEON_VM_PAGE_VALID) |
value = addr; |
else |
value = 0; |
/* for physically contiguous pages (vram) */ |
ib->ptr[ib->length_dw++] = DMA_PTE_PDE_PACKET(ndw); |
ib->ptr[ib->length_dw++] = pe; /* dst addr */ |
ib->ptr[ib->length_dw++] = upper_32_bits(pe) & 0xff; |
ib->ptr[ib->length_dw++] = r600_flags; /* mask */ |
ib->ptr[ib->length_dw++] = 0; |
ib->ptr[ib->length_dw++] = value; /* value */ |
ib->ptr[ib->length_dw++] = upper_32_bits(value); |
ib->ptr[ib->length_dw++] = incr; /* increment size */ |
ib->ptr[ib->length_dw++] = 0; |
pe += ndw * 4; |
addr += (ndw / 2) * incr; |
count -= ndw / 2; |
} |
} |
while (ib->length_dw & 0x7) |
ib->ptr[ib->length_dw++] = DMA_PACKET(DMA_PACKET_NOP, 0, 0, 0); |
} |
} |
/** |
* cayman_vm_flush - vm flush using the CP |
/drivers/video/drm/radeon/nid.h |
---|
45,10 → 45,24 |
#define ARUBA_GB_ADDR_CONFIG_GOLDEN 0x12010001 |
#define DMIF_ADDR_CONFIG 0xBD4 |
/* DCE6 only */ |
#define DMIF_ADDR_CALC 0xC00 |
#define SRBM_GFX_CNTL 0x0E44 |
#define RINGID(x) (((x) & 0x3) << 0) |
#define VMID(x) (((x) & 0x7) << 0) |
#define SRBM_STATUS 0x0E50 |
#define RLC_RQ_PENDING (1 << 3) |
#define GRBM_RQ_PENDING (1 << 5) |
#define VMC_BUSY (1 << 8) |
#define MCB_BUSY (1 << 9) |
#define MCB_NON_DISPLAY_BUSY (1 << 10) |
#define MCC_BUSY (1 << 11) |
#define MCD_BUSY (1 << 12) |
#define SEM_BUSY (1 << 14) |
#define RLC_BUSY (1 << 15) |
#define IH_BUSY (1 << 17) |
#define SRBM_SOFT_RESET 0x0E60 |
#define SOFT_RESET_BIF (1 << 1) |
68,6 → 82,10 |
#define SOFT_RESET_REGBB (1 << 22) |
#define SOFT_RESET_ORB (1 << 23) |
#define SRBM_STATUS2 0x0EC4 |
#define DMA_BUSY (1 << 5) |
#define DMA1_BUSY (1 << 6) |
#define VM_CONTEXT0_REQUEST_RESPONSE 0x1470 |
#define REQUEST_TYPE(x) (((x) & 0xf) << 0) |
#define RESPONSE_TYPE_MASK 0x000000F0 |
472,18 → 490,21 |
# define CACHE_FLUSH_AND_INV_EVENT (0x16 << 0) |
/* |
* UVD |
*/ |
#define UVD_SEMA_ADDR_LOW 0xEF00 |
#define UVD_SEMA_ADDR_HIGH 0xEF04 |
#define UVD_SEMA_CMD 0xEF08 |
#define UVD_UDEC_ADDR_CONFIG 0xEF4C |
#define UVD_UDEC_DB_ADDR_CONFIG 0xEF50 |
#define UVD_UDEC_DBW_ADDR_CONFIG 0xEF54 |
#define UVD_RBC_RB_RPTR 0xF690 |
#define UVD_RBC_RB_WPTR 0xF694 |
/* |
* PM4 |
*/ |
#define PACKET_TYPE0 0 |
#define PACKET_TYPE1 1 |
#define PACKET_TYPE2 2 |
#define PACKET_TYPE3 3 |
#define CP_PACKET_GET_TYPE(h) (((h) >> 30) & 3) |
#define CP_PACKET_GET_COUNT(h) (((h) >> 16) & 0x3FFF) |
#define CP_PACKET0_GET_REG(h) (((h) & 0xFFFF) << 2) |
#define CP_PACKET3_GET_OPCODE(h) (((h) >> 8) & 0xFF) |
#define PACKET0(reg, n) ((PACKET_TYPE0 << 30) | \ |
#define PACKET0(reg, n) ((RADEON_PACKET_TYPE0 << 30) | \ |
(((reg) >> 2) & 0xFFFF) | \ |
((n) & 0x3FFF) << 16) |
#define CP_PACKET2 0x80000000 |
492,7 → 513,7 |
#define PACKET2(v) (CP_PACKET2 | REG_SET(PACKET2_PAD, (v))) |
#define PACKET3(op, n) ((PACKET_TYPE3 << 30) | \ |
#define PACKET3(op, n) ((RADEON_PACKET_TYPE3 << 30) | \ |
(((op) & 0xFF) << 8) | \ |
((n) & 0x3FFF) << 16) |
663,6 → 684,11 |
(((vmid) & 0xF) << 20) | \ |
(((n) & 0xFFFFF) << 0)) |
#define DMA_PTE_PDE_PACKET(n) ((2 << 28) | \ |
(1 << 26) | \ |
(1 << 21) | \ |
(((n) & 0xFFFFF) << 0)) |
/* async DMA Packet types */ |
#define DMA_PACKET_WRITE 0x2 |
#define DMA_PACKET_COPY 0x3 |
/drivers/video/drm/radeon/pci.c |
---|
1,5 → 1,6 |
#include <linux/kernel.h> |
#include <linux/types.h> |
#include <linux/export.h> |
#include <linux/mutex.h> |
#include <linux/mod_devicetable.h> |
635,7 → 636,9 |
/* Create a virtual mapping cookie for an IO port range */ |
void __iomem *ioport_map(unsigned long port, unsigned int nr) |
{ |
return (void __iomem *) port; |
if (port > PIO_MASK) |
return NULL; |
return (void __iomem *) (unsigned long) (port + PIO_OFFSET); |
} |
void __iomem *pci_iomap(struct pci_dev *dev, int bar, unsigned long maxlen) |
786,7 → 789,8 |
start = (loff_t)0xC0000; |
*size = 0x20000; /* cover C000:0 through E000:0 */ |
} else { |
if (res->flags & (IORESOURCE_ROM_COPY | IORESOURCE_ROM_BIOS_COPY)) { |
if (res->flags & |
(IORESOURCE_ROM_COPY | IORESOURCE_ROM_BIOS_COPY)) { |
*size = pci_resource_len(pdev, PCI_ROM_RESOURCE); |
return (void __iomem *)(unsigned long) |
pci_resource_start(pdev, PCI_ROM_RESOURCE); |
841,15 → 845,6 |
pci_disable_rom(pdev); |
} |
int pci_set_dma_mask(struct pci_dev *dev, u64 mask) |
{ |
dev->dma_mask = mask; |
return 0; |
} |
static void __pci_set_master(struct pci_dev *dev, bool enable) |
{ |
u16 old_cmd, cmd; |
/drivers/video/drm/radeon/r100.c |
---|
67,6 → 67,38 |
* and others in some cases. |
*/ |
static bool r100_is_in_vblank(struct radeon_device *rdev, int crtc) |
{ |
if (crtc == 0) { |
if (RREG32(RADEON_CRTC_STATUS) & RADEON_CRTC_VBLANK_CUR) |
return true; |
else |
return false; |
} else { |
if (RREG32(RADEON_CRTC2_STATUS) & RADEON_CRTC2_VBLANK_CUR) |
return true; |
else |
return false; |
} |
} |
static bool r100_is_counter_moving(struct radeon_device *rdev, int crtc) |
{ |
u32 vline1, vline2; |
if (crtc == 0) { |
vline1 = (RREG32(RADEON_CRTC_VLINE_CRNT_VLINE) >> 16) & RADEON_CRTC_V_TOTAL; |
vline2 = (RREG32(RADEON_CRTC_VLINE_CRNT_VLINE) >> 16) & RADEON_CRTC_V_TOTAL; |
} else { |
vline1 = (RREG32(RADEON_CRTC2_VLINE_CRNT_VLINE) >> 16) & RADEON_CRTC_V_TOTAL; |
vline2 = (RREG32(RADEON_CRTC2_VLINE_CRNT_VLINE) >> 16) & RADEON_CRTC_V_TOTAL; |
} |
if (vline1 != vline2) |
return true; |
else |
return false; |
} |
/** |
* r100_wait_for_vblank - vblank wait asic callback. |
* |
77,39 → 109,36 |
*/ |
void r100_wait_for_vblank(struct radeon_device *rdev, int crtc) |
{ |
int i; |
unsigned i = 0; |
if (crtc >= rdev->num_crtc) |
return; |
if (crtc == 0) { |
if (RREG32(RADEON_CRTC_GEN_CNTL) & RADEON_CRTC_EN) { |
for (i = 0; i < rdev->usec_timeout; i++) { |
if (!(RREG32(RADEON_CRTC_STATUS) & RADEON_CRTC_VBLANK_CUR)) |
break; |
udelay(1); |
if (!(RREG32(RADEON_CRTC_GEN_CNTL) & RADEON_CRTC_EN)) |
return; |
} else { |
if (!(RREG32(RADEON_CRTC2_GEN_CNTL) & RADEON_CRTC2_EN)) |
return; |
} |
for (i = 0; i < rdev->usec_timeout; i++) { |
if (RREG32(RADEON_CRTC_STATUS) & RADEON_CRTC_VBLANK_CUR) |
/* depending on when we hit vblank, we may be close to active; if so, |
* wait for another frame. |
*/ |
while (r100_is_in_vblank(rdev, crtc)) { |
if (i++ % 100 == 0) { |
if (!r100_is_counter_moving(rdev, crtc)) |
break; |
udelay(1); |
} |
} |
} else { |
if (RREG32(RADEON_CRTC2_GEN_CNTL) & RADEON_CRTC2_EN) { |
for (i = 0; i < rdev->usec_timeout; i++) { |
if (!(RREG32(RADEON_CRTC2_STATUS) & RADEON_CRTC2_VBLANK_CUR)) |
while (!r100_is_in_vblank(rdev, crtc)) { |
if (i++ % 100 == 0) { |
if (!r100_is_counter_moving(rdev, crtc)) |
break; |
udelay(1); |
} |
for (i = 0; i < rdev->usec_timeout; i++) { |
if (RREG32(RADEON_CRTC2_STATUS) & RADEON_CRTC2_VBLANK_CUR) |
break; |
udelay(1); |
} |
} |
} |
} |
u32 r100_page_flip(struct radeon_device *rdev, int crtc_id, u64 crtc_base) |
{ |
struct radeon_crtc *radeon_crtc = rdev->mode_info.crtcs[crtc_id]; |
857,11 → 886,11 |
struct radeon_cs_reloc *reloc; |
u32 value; |
r = r100_cs_packet_next_reloc(p, &reloc); |
r = radeon_cs_packet_next_reloc(p, &reloc, 0); |
if (r) { |
DRM_ERROR("No reloc for ib[%d]=0x%04X\n", |
idx, reg); |
r100_cs_dump_packet(p, pkt); |
radeon_cs_dump_packet(p, pkt); |
return r; |
} |
875,7 → 904,7 |
if (reloc->lobj.tiling_flags & RADEON_TILING_MICRO) { |
if (reg == RADEON_SRC_PITCH_OFFSET) { |
DRM_ERROR("Cannot src blit from microtiled surface\n"); |
r100_cs_dump_packet(p, pkt); |
radeon_cs_dump_packet(p, pkt); |
return -EINVAL; |
} |
tile_flags |= RADEON_DST_TILE_MICRO; |
905,16 → 934,16 |
if (c > 16) { |
DRM_ERROR("Only 16 vertex buffers are allowed %d\n", |
pkt->opcode); |
r100_cs_dump_packet(p, pkt); |
radeon_cs_dump_packet(p, pkt); |
return -EINVAL; |
} |
track->num_arrays = c; |
for (i = 0; i < (c - 1); i+=2, idx+=3) { |
r = r100_cs_packet_next_reloc(p, &reloc); |
r = radeon_cs_packet_next_reloc(p, &reloc, 0); |
if (r) { |
DRM_ERROR("No reloc for packet3 %d\n", |
pkt->opcode); |
r100_cs_dump_packet(p, pkt); |
radeon_cs_dump_packet(p, pkt); |
return r; |
} |
idx_value = radeon_get_ib_value(p, idx); |
923,11 → 952,11 |
track->arrays[i + 0].esize = idx_value >> 8; |
track->arrays[i + 0].robj = reloc->robj; |
track->arrays[i + 0].esize &= 0x7F; |
r = r100_cs_packet_next_reloc(p, &reloc); |
r = radeon_cs_packet_next_reloc(p, &reloc, 0); |
if (r) { |
DRM_ERROR("No reloc for packet3 %d\n", |
pkt->opcode); |
r100_cs_dump_packet(p, pkt); |
radeon_cs_dump_packet(p, pkt); |
return r; |
} |
ib[idx+2] = radeon_get_ib_value(p, idx + 2) + ((u32)reloc->lobj.gpu_offset); |
936,11 → 965,11 |
track->arrays[i + 1].esize &= 0x7F; |
} |
if (c & 1) { |
r = r100_cs_packet_next_reloc(p, &reloc); |
r = radeon_cs_packet_next_reloc(p, &reloc, 0); |
if (r) { |
DRM_ERROR("No reloc for packet3 %d\n", |
pkt->opcode); |
r100_cs_dump_packet(p, pkt); |
radeon_cs_dump_packet(p, pkt); |
return r; |
} |
idx_value = radeon_get_ib_value(p, idx); |
1086,7 → 1115,7 |
ib = p->ib.ptr; |
/* parse the wait until */ |
r = r100_cs_packet_parse(p, &waitreloc, p->idx); |
r = radeon_cs_packet_parse(p, &waitreloc, p->idx); |
if (r) |
return r; |
1103,7 → 1132,7 |
} |
/* jump over the NOP */ |
r = r100_cs_packet_parse(p, &p3reloc, p->idx + waitreloc.count + 2); |
r = radeon_cs_packet_parse(p, &p3reloc, p->idx + waitreloc.count + 2); |
if (r) |
return r; |
1113,7 → 1142,7 |
header = radeon_get_ib_value(p, h_idx); |
crtc_id = radeon_get_ib_value(p, h_idx + 5); |
reg = CP_PACKET0_GET_REG(header); |
reg = R100_CP_PACKET0_GET_REG(header); |
obj = drm_mode_object_find(p->rdev->ddev, crtc_id, DRM_MODE_OBJECT_CRTC); |
if (!obj) { |
DRM_ERROR("cannot find crtc %d\n", crtc_id); |
1148,54 → 1177,6 |
return 0; |
} |
/** |
* r100_cs_packet_next_reloc() - parse next packet which should be reloc packet3 |
* @parser: parser structure holding parsing context. |
* @data: pointer to relocation data |
* @offset_start: starting offset |
* @offset_mask: offset mask (to align start offset on) |
* @reloc: reloc informations |
* |
* Check next packet is relocation packet3, do bo validation and compute |
* GPU offset using the provided start. |
**/ |
int r100_cs_packet_next_reloc(struct radeon_cs_parser *p, |
struct radeon_cs_reloc **cs_reloc) |
{ |
struct radeon_cs_chunk *relocs_chunk; |
struct radeon_cs_packet p3reloc; |
unsigned idx; |
int r; |
if (p->chunk_relocs_idx == -1) { |
DRM_ERROR("No relocation chunk !\n"); |
return -EINVAL; |
} |
*cs_reloc = NULL; |
relocs_chunk = &p->chunks[p->chunk_relocs_idx]; |
r = r100_cs_packet_parse(p, &p3reloc, p->idx); |
if (r) { |
return r; |
} |
p->idx += p3reloc.count + 2; |
if (p3reloc.type != PACKET_TYPE3 || p3reloc.opcode != PACKET3_NOP) { |
DRM_ERROR("No packet3 for relocation for packet at %d.\n", |
p3reloc.idx); |
r100_cs_dump_packet(p, &p3reloc); |
return -EINVAL; |
} |
idx = radeon_get_ib_value(p, p3reloc.idx + 1); |
if (idx >= relocs_chunk->length_dw) { |
DRM_ERROR("Relocs at %d after relocations chunk end %d !\n", |
idx, relocs_chunk->length_dw); |
r100_cs_dump_packet(p, &p3reloc); |
return -EINVAL; |
} |
/* FIXME: we assume reloc size is 4 dwords */ |
*cs_reloc = p->relocs_ptr[(idx / 4)]; |
return 0; |
} |
static int r100_get_vtx_size(uint32_t vtx_fmt) |
{ |
int vtx_size; |
1273,7 → 1254,7 |
if (r) { |
DRM_ERROR("No reloc for ib[%d]=0x%04X\n", |
idx, reg); |
r100_cs_dump_packet(p, pkt); |
radeon_cs_dump_packet(p, pkt); |
return r; |
} |
break; |
1286,11 → 1267,11 |
return r; |
break; |
case RADEON_RB3D_DEPTHOFFSET: |
r = r100_cs_packet_next_reloc(p, &reloc); |
r = radeon_cs_packet_next_reloc(p, &reloc, 0); |
if (r) { |
DRM_ERROR("No reloc for ib[%d]=0x%04X\n", |
idx, reg); |
r100_cs_dump_packet(p, pkt); |
radeon_cs_dump_packet(p, pkt); |
return r; |
} |
track->zb.robj = reloc->robj; |
1299,11 → 1280,11 |
ib[idx] = idx_value + ((u32)reloc->lobj.gpu_offset); |
break; |
case RADEON_RB3D_COLOROFFSET: |
r = r100_cs_packet_next_reloc(p, &reloc); |
r = radeon_cs_packet_next_reloc(p, &reloc, 0); |
if (r) { |
DRM_ERROR("No reloc for ib[%d]=0x%04X\n", |
idx, reg); |
r100_cs_dump_packet(p, pkt); |
radeon_cs_dump_packet(p, pkt); |
return r; |
} |
track->cb[0].robj = reloc->robj; |
1315,11 → 1296,11 |
case RADEON_PP_TXOFFSET_1: |
case RADEON_PP_TXOFFSET_2: |
i = (reg - RADEON_PP_TXOFFSET_0) / 24; |
r = r100_cs_packet_next_reloc(p, &reloc); |
r = radeon_cs_packet_next_reloc(p, &reloc, 0); |
if (r) { |
DRM_ERROR("No reloc for ib[%d]=0x%04X\n", |
idx, reg); |
r100_cs_dump_packet(p, pkt); |
radeon_cs_dump_packet(p, pkt); |
return r; |
} |
if (!(p->cs_flags & RADEON_CS_KEEP_TILING_FLAGS)) { |
1342,11 → 1323,11 |
case RADEON_PP_CUBIC_OFFSET_T0_3: |
case RADEON_PP_CUBIC_OFFSET_T0_4: |
i = (reg - RADEON_PP_CUBIC_OFFSET_T0_0) / 4; |
r = r100_cs_packet_next_reloc(p, &reloc); |
r = radeon_cs_packet_next_reloc(p, &reloc, 0); |
if (r) { |
DRM_ERROR("No reloc for ib[%d]=0x%04X\n", |
idx, reg); |
r100_cs_dump_packet(p, pkt); |
radeon_cs_dump_packet(p, pkt); |
return r; |
} |
track->textures[0].cube_info[i].offset = idx_value; |
1360,11 → 1341,11 |
case RADEON_PP_CUBIC_OFFSET_T1_3: |
case RADEON_PP_CUBIC_OFFSET_T1_4: |
i = (reg - RADEON_PP_CUBIC_OFFSET_T1_0) / 4; |
r = r100_cs_packet_next_reloc(p, &reloc); |
r = radeon_cs_packet_next_reloc(p, &reloc, 0); |
if (r) { |
DRM_ERROR("No reloc for ib[%d]=0x%04X\n", |
idx, reg); |
r100_cs_dump_packet(p, pkt); |
radeon_cs_dump_packet(p, pkt); |
return r; |
} |
track->textures[1].cube_info[i].offset = idx_value; |
1378,11 → 1359,11 |
case RADEON_PP_CUBIC_OFFSET_T2_3: |
case RADEON_PP_CUBIC_OFFSET_T2_4: |
i = (reg - RADEON_PP_CUBIC_OFFSET_T2_0) / 4; |
r = r100_cs_packet_next_reloc(p, &reloc); |
r = radeon_cs_packet_next_reloc(p, &reloc, 0); |
if (r) { |
DRM_ERROR("No reloc for ib[%d]=0x%04X\n", |
idx, reg); |
r100_cs_dump_packet(p, pkt); |
radeon_cs_dump_packet(p, pkt); |
return r; |
} |
track->textures[2].cube_info[i].offset = idx_value; |
1396,11 → 1377,11 |
track->zb_dirty = true; |
break; |
case RADEON_RB3D_COLORPITCH: |
r = r100_cs_packet_next_reloc(p, &reloc); |
r = radeon_cs_packet_next_reloc(p, &reloc, 0); |
if (r) { |
DRM_ERROR("No reloc for ib[%d]=0x%04X\n", |
idx, reg); |
r100_cs_dump_packet(p, pkt); |
radeon_cs_dump_packet(p, pkt); |
return r; |
} |
if (!(p->cs_flags & RADEON_CS_KEEP_TILING_FLAGS)) { |
1467,11 → 1448,11 |
track->zb_dirty = true; |
break; |
case RADEON_RB3D_ZPASS_ADDR: |
r = r100_cs_packet_next_reloc(p, &reloc); |
r = radeon_cs_packet_next_reloc(p, &reloc, 0); |
if (r) { |
DRM_ERROR("No reloc for ib[%d]=0x%04X\n", |
idx, reg); |
r100_cs_dump_packet(p, pkt); |
radeon_cs_dump_packet(p, pkt); |
return r; |
} |
ib[idx] = idx_value + ((u32)reloc->lobj.gpu_offset); |
1628,10 → 1609,10 |
return r; |
break; |
case PACKET3_INDX_BUFFER: |
r = r100_cs_packet_next_reloc(p, &reloc); |
r = radeon_cs_packet_next_reloc(p, &reloc, 0); |
if (r) { |
DRM_ERROR("No reloc for packet3 %d\n", pkt->opcode); |
r100_cs_dump_packet(p, pkt); |
radeon_cs_dump_packet(p, pkt); |
return r; |
} |
ib[idx+1] = radeon_get_ib_value(p, idx+1) + ((u32)reloc->lobj.gpu_offset); |
1642,10 → 1623,10 |
break; |
case 0x23: |
/* 3D_RNDR_GEN_INDX_PRIM on r100/r200 */ |
r = r100_cs_packet_next_reloc(p, &reloc); |
r = radeon_cs_packet_next_reloc(p, &reloc, 0); |
if (r) { |
DRM_ERROR("No reloc for packet3 %d\n", pkt->opcode); |
r100_cs_dump_packet(p, pkt); |
radeon_cs_dump_packet(p, pkt); |
return r; |
} |
ib[idx] = radeon_get_ib_value(p, idx) + ((u32)reloc->lobj.gpu_offset); |
1742,13 → 1723,13 |
r100_cs_track_clear(p->rdev, track); |
p->track = track; |
do { |
r = r100_cs_packet_parse(p, &pkt, p->idx); |
r = radeon_cs_packet_parse(p, &pkt, p->idx); |
if (r) { |
return r; |
} |
p->idx += pkt.count + 2; |
switch (pkt.type) { |
case PACKET_TYPE0: |
case RADEON_PACKET_TYPE0: |
if (p->rdev->family >= CHIP_R200) |
r = r100_cs_parse_packet0(p, &pkt, |
p->rdev->config.r100.reg_safe_bm, |
1760,9 → 1741,9 |
p->rdev->config.r100.reg_safe_bm_size, |
&r100_packet0_check); |
break; |
case PACKET_TYPE2: |
case RADEON_PACKET_TYPE2: |
break; |
case PACKET_TYPE3: |
case RADEON_PACKET_TYPE3: |
r = r100_packet3_check(p, &pkt); |
break; |
default: |
1770,9 → 1751,8 |
pkt.type); |
return -EINVAL; |
} |
if (r) { |
if (r) |
return r; |
} |
} while (p->idx < p->chunks[p->chunk_ib_idx].length_dw); |
return 0; |
} |
3593,6 → 3573,12 |
} |
/* Enable IRQ */ |
if (!rdev->irq.installed) { |
r = radeon_irq_kms_init(rdev); |
if (r) |
return r; |
} |
r100_irq_set(rdev); |
rdev->config.r100.hdp_cntl = RREG32(RADEON_HOST_PATH_CNTL); |
/* 1M ring buffer */ |
3691,9 → 3677,6 |
r = radeon_fence_driver_init(rdev); |
if (r) |
return r; |
r = radeon_irq_kms_init(rdev); |
if (r) |
return r; |
/* Memory manager */ |
r = radeon_bo_init(rdev); |
if (r) |
/drivers/video/drm/radeon/r100d.h |
---|
64,17 → 64,6 |
REG_SET(PACKET3_IT_OPCODE, (op)) | \ |
REG_SET(PACKET3_COUNT, (n))) |
#define PACKET_TYPE0 0 |
#define PACKET_TYPE1 1 |
#define PACKET_TYPE2 2 |
#define PACKET_TYPE3 3 |
#define CP_PACKET_GET_TYPE(h) (((h) >> 30) & 3) |
#define CP_PACKET_GET_COUNT(h) (((h) >> 16) & 0x3FFF) |
#define CP_PACKET0_GET_REG(h) (((h) & 0x1FFF) << 2) |
#define CP_PACKET0_GET_ONE_REG_WR(h) (((h) >> 15) & 1) |
#define CP_PACKET3_GET_OPCODE(h) (((h) >> 8) & 0xFF) |
/* Registers */ |
#define R_0000F0_RBBM_SOFT_RESET 0x0000F0 |
#define S_0000F0_SOFT_RESET_CP(x) (((x) & 0x1) << 0) |
/drivers/video/drm/radeon/r200.c |
---|
165,7 → 165,7 |
if (r) { |
DRM_ERROR("No reloc for ib[%d]=0x%04X\n", |
idx, reg); |
r100_cs_dump_packet(p, pkt); |
radeon_cs_dump_packet(p, pkt); |
return r; |
} |
break; |
178,11 → 178,11 |
return r; |
break; |
case RADEON_RB3D_DEPTHOFFSET: |
r = r100_cs_packet_next_reloc(p, &reloc); |
r = radeon_cs_packet_next_reloc(p, &reloc, 0); |
if (r) { |
DRM_ERROR("No reloc for ib[%d]=0x%04X\n", |
idx, reg); |
r100_cs_dump_packet(p, pkt); |
radeon_cs_dump_packet(p, pkt); |
return r; |
} |
track->zb.robj = reloc->robj; |
191,11 → 191,11 |
ib[idx] = idx_value + ((u32)reloc->lobj.gpu_offset); |
break; |
case RADEON_RB3D_COLOROFFSET: |
r = r100_cs_packet_next_reloc(p, &reloc); |
r = radeon_cs_packet_next_reloc(p, &reloc, 0); |
if (r) { |
DRM_ERROR("No reloc for ib[%d]=0x%04X\n", |
idx, reg); |
r100_cs_dump_packet(p, pkt); |
radeon_cs_dump_packet(p, pkt); |
return r; |
} |
track->cb[0].robj = reloc->robj; |
210,11 → 210,11 |
case R200_PP_TXOFFSET_4: |
case R200_PP_TXOFFSET_5: |
i = (reg - R200_PP_TXOFFSET_0) / 24; |
r = r100_cs_packet_next_reloc(p, &reloc); |
r = radeon_cs_packet_next_reloc(p, &reloc, 0); |
if (r) { |
DRM_ERROR("No reloc for ib[%d]=0x%04X\n", |
idx, reg); |
r100_cs_dump_packet(p, pkt); |
radeon_cs_dump_packet(p, pkt); |
return r; |
} |
if (!(p->cs_flags & RADEON_CS_KEEP_TILING_FLAGS)) { |
263,11 → 263,11 |
case R200_PP_CUBIC_OFFSET_F5_5: |
i = (reg - R200_PP_TXOFFSET_0) / 24; |
face = (reg - ((i * 24) + R200_PP_TXOFFSET_0)) / 4; |
r = r100_cs_packet_next_reloc(p, &reloc); |
r = radeon_cs_packet_next_reloc(p, &reloc, 0); |
if (r) { |
DRM_ERROR("No reloc for ib[%d]=0x%04X\n", |
idx, reg); |
r100_cs_dump_packet(p, pkt); |
radeon_cs_dump_packet(p, pkt); |
return r; |
} |
track->textures[i].cube_info[face - 1].offset = idx_value; |
281,11 → 281,11 |
track->zb_dirty = true; |
break; |
case RADEON_RB3D_COLORPITCH: |
r = r100_cs_packet_next_reloc(p, &reloc); |
r = radeon_cs_packet_next_reloc(p, &reloc, 0); |
if (r) { |
DRM_ERROR("No reloc for ib[%d]=0x%04X\n", |
idx, reg); |
r100_cs_dump_packet(p, pkt); |
radeon_cs_dump_packet(p, pkt); |
return r; |
} |
358,11 → 358,11 |
track->zb_dirty = true; |
break; |
case RADEON_RB3D_ZPASS_ADDR: |
r = r100_cs_packet_next_reloc(p, &reloc); |
r = radeon_cs_packet_next_reloc(p, &reloc, 0); |
if (r) { |
DRM_ERROR("No reloc for ib[%d]=0x%04X\n", |
idx, reg); |
r100_cs_dump_packet(p, pkt); |
radeon_cs_dump_packet(p, pkt); |
return r; |
} |
ib[idx] = idx_value + ((u32)reloc->lobj.gpu_offset); |
/drivers/video/drm/radeon/r300.c |
---|
618,7 → 618,7 |
if (r) { |
DRM_ERROR("No reloc for ib[%d]=0x%04X\n", |
idx, reg); |
r100_cs_dump_packet(p, pkt); |
radeon_cs_dump_packet(p, pkt); |
return r; |
} |
break; |
633,11 → 633,11 |
case R300_RB3D_COLOROFFSET2: |
case R300_RB3D_COLOROFFSET3: |
i = (reg - R300_RB3D_COLOROFFSET0) >> 2; |
r = r100_cs_packet_next_reloc(p, &reloc); |
r = radeon_cs_packet_next_reloc(p, &reloc, 0); |
if (r) { |
DRM_ERROR("No reloc for ib[%d]=0x%04X\n", |
idx, reg); |
r100_cs_dump_packet(p, pkt); |
radeon_cs_dump_packet(p, pkt); |
return r; |
} |
track->cb[i].robj = reloc->robj; |
646,11 → 646,11 |
ib[idx] = idx_value + ((u32)reloc->lobj.gpu_offset); |
break; |
case R300_ZB_DEPTHOFFSET: |
r = r100_cs_packet_next_reloc(p, &reloc); |
r = radeon_cs_packet_next_reloc(p, &reloc, 0); |
if (r) { |
DRM_ERROR("No reloc for ib[%d]=0x%04X\n", |
idx, reg); |
r100_cs_dump_packet(p, pkt); |
radeon_cs_dump_packet(p, pkt); |
return r; |
} |
track->zb.robj = reloc->robj; |
675,11 → 675,11 |
case R300_TX_OFFSET_0+56: |
case R300_TX_OFFSET_0+60: |
i = (reg - R300_TX_OFFSET_0) >> 2; |
r = r100_cs_packet_next_reloc(p, &reloc); |
r = radeon_cs_packet_next_reloc(p, &reloc, 0); |
if (r) { |
DRM_ERROR("No reloc for ib[%d]=0x%04X\n", |
idx, reg); |
r100_cs_dump_packet(p, pkt); |
radeon_cs_dump_packet(p, pkt); |
return r; |
} |
748,11 → 748,11 |
/* RB3D_COLORPITCH2 */ |
/* RB3D_COLORPITCH3 */ |
if (!(p->cs_flags & RADEON_CS_KEEP_TILING_FLAGS)) { |
r = r100_cs_packet_next_reloc(p, &reloc); |
r = radeon_cs_packet_next_reloc(p, &reloc, 0); |
if (r) { |
DRM_ERROR("No reloc for ib[%d]=0x%04X\n", |
idx, reg); |
r100_cs_dump_packet(p, pkt); |
radeon_cs_dump_packet(p, pkt); |
return r; |
} |
833,11 → 833,11 |
case 0x4F24: |
/* ZB_DEPTHPITCH */ |
if (!(p->cs_flags & RADEON_CS_KEEP_TILING_FLAGS)) { |
r = r100_cs_packet_next_reloc(p, &reloc); |
r = radeon_cs_packet_next_reloc(p, &reloc, 0); |
if (r) { |
DRM_ERROR("No reloc for ib[%d]=0x%04X\n", |
idx, reg); |
r100_cs_dump_packet(p, pkt); |
radeon_cs_dump_packet(p, pkt); |
return r; |
} |
1048,11 → 1048,11 |
track->tex_dirty = true; |
break; |
case R300_ZB_ZPASS_ADDR: |
r = r100_cs_packet_next_reloc(p, &reloc); |
r = radeon_cs_packet_next_reloc(p, &reloc, 0); |
if (r) { |
DRM_ERROR("No reloc for ib[%d]=0x%04X\n", |
idx, reg); |
r100_cs_dump_packet(p, pkt); |
radeon_cs_dump_packet(p, pkt); |
return r; |
} |
ib[idx] = idx_value + ((u32)reloc->lobj.gpu_offset); |
1090,11 → 1090,11 |
track->cb_dirty = true; |
break; |
case R300_RB3D_AARESOLVE_OFFSET: |
r = r100_cs_packet_next_reloc(p, &reloc); |
r = radeon_cs_packet_next_reloc(p, &reloc, 0); |
if (r) { |
DRM_ERROR("No reloc for ib[%d]=0x%04X\n", |
idx, reg); |
r100_cs_dump_packet(p, pkt); |
radeon_cs_dump_packet(p, pkt); |
return r; |
} |
track->aa.robj = reloc->robj; |
1159,10 → 1159,10 |
return r; |
break; |
case PACKET3_INDX_BUFFER: |
r = r100_cs_packet_next_reloc(p, &reloc); |
r = radeon_cs_packet_next_reloc(p, &reloc, 0); |
if (r) { |
DRM_ERROR("No reloc for packet3 %d\n", pkt->opcode); |
r100_cs_dump_packet(p, pkt); |
radeon_cs_dump_packet(p, pkt); |
return r; |
} |
ib[idx+1] = radeon_get_ib_value(p, idx + 1) + ((u32)reloc->lobj.gpu_offset); |
1260,21 → 1260,21 |
r100_cs_track_clear(p->rdev, track); |
p->track = track; |
do { |
r = r100_cs_packet_parse(p, &pkt, p->idx); |
r = radeon_cs_packet_parse(p, &pkt, p->idx); |
if (r) { |
return r; |
} |
p->idx += pkt.count + 2; |
switch (pkt.type) { |
case PACKET_TYPE0: |
case RADEON_PACKET_TYPE0: |
r = r100_cs_parse_packet0(p, &pkt, |
p->rdev->config.r300.reg_safe_bm, |
p->rdev->config.r300.reg_safe_bm_size, |
&r300_packet0_check); |
break; |
case PACKET_TYPE2: |
case RADEON_PACKET_TYPE2: |
break; |
case PACKET_TYPE3: |
case RADEON_PACKET_TYPE3: |
r = r300_packet3_check(p, &pkt); |
break; |
default: |
1387,6 → 1387,12 |
} |
/* Enable IRQ */ |
if (!rdev->irq.installed) { |
r = radeon_irq_kms_init(rdev); |
if (r) |
return r; |
} |
r100_irq_set(rdev); |
rdev->config.r300.hdp_cntl = RREG32(RADEON_HOST_PATH_CNTL); |
/* 1M ring buffer */ |
1462,9 → 1468,6 |
r = radeon_fence_driver_init(rdev); |
if (r) |
return r; |
r = radeon_irq_kms_init(rdev); |
if (r) |
return r; |
/* Memory manager */ |
r = radeon_bo_init(rdev); |
if (r) |
/drivers/video/drm/radeon/r300d.h |
---|
65,17 → 65,6 |
REG_SET(PACKET3_IT_OPCODE, (op)) | \ |
REG_SET(PACKET3_COUNT, (n))) |
#define PACKET_TYPE0 0 |
#define PACKET_TYPE1 1 |
#define PACKET_TYPE2 2 |
#define PACKET_TYPE3 3 |
#define CP_PACKET_GET_TYPE(h) (((h) >> 30) & 3) |
#define CP_PACKET_GET_COUNT(h) (((h) >> 16) & 0x3FFF) |
#define CP_PACKET0_GET_REG(h) (((h) & 0x1FFF) << 2) |
#define CP_PACKET0_GET_ONE_REG_WR(h) (((h) >> 15) & 1) |
#define CP_PACKET3_GET_OPCODE(h) (((h) >> 8) & 0xFF) |
/* Registers */ |
#define R_000148_MC_FB_LOCATION 0x000148 |
#define S_000148_MC_FB_START(x) (((x) & 0xFFFF) << 0) |
/drivers/video/drm/radeon/r420.c |
---|
36,6 → 36,45 |
#include "r420d.h" |
#include "r420_reg_safe.h" |
void r420_pm_init_profile(struct radeon_device *rdev) |
{ |
/* default */ |
rdev->pm.profiles[PM_PROFILE_DEFAULT_IDX].dpms_off_ps_idx = rdev->pm.default_power_state_index; |
rdev->pm.profiles[PM_PROFILE_DEFAULT_IDX].dpms_on_ps_idx = rdev->pm.default_power_state_index; |
rdev->pm.profiles[PM_PROFILE_DEFAULT_IDX].dpms_off_cm_idx = 0; |
rdev->pm.profiles[PM_PROFILE_DEFAULT_IDX].dpms_on_cm_idx = 0; |
/* low sh */ |
rdev->pm.profiles[PM_PROFILE_LOW_SH_IDX].dpms_off_ps_idx = 0; |
rdev->pm.profiles[PM_PROFILE_LOW_SH_IDX].dpms_on_ps_idx = 0; |
rdev->pm.profiles[PM_PROFILE_LOW_SH_IDX].dpms_off_cm_idx = 0; |
rdev->pm.profiles[PM_PROFILE_LOW_SH_IDX].dpms_on_cm_idx = 0; |
/* mid sh */ |
rdev->pm.profiles[PM_PROFILE_MID_SH_IDX].dpms_off_ps_idx = 0; |
rdev->pm.profiles[PM_PROFILE_MID_SH_IDX].dpms_on_ps_idx = 1; |
rdev->pm.profiles[PM_PROFILE_MID_SH_IDX].dpms_off_cm_idx = 0; |
rdev->pm.profiles[PM_PROFILE_MID_SH_IDX].dpms_on_cm_idx = 0; |
/* high sh */ |
rdev->pm.profiles[PM_PROFILE_HIGH_SH_IDX].dpms_off_ps_idx = 0; |
rdev->pm.profiles[PM_PROFILE_HIGH_SH_IDX].dpms_on_ps_idx = rdev->pm.default_power_state_index; |
rdev->pm.profiles[PM_PROFILE_HIGH_SH_IDX].dpms_off_cm_idx = 0; |
rdev->pm.profiles[PM_PROFILE_HIGH_SH_IDX].dpms_on_cm_idx = 0; |
/* low mh */ |
rdev->pm.profiles[PM_PROFILE_LOW_MH_IDX].dpms_off_ps_idx = 0; |
rdev->pm.profiles[PM_PROFILE_LOW_MH_IDX].dpms_on_ps_idx = rdev->pm.default_power_state_index; |
rdev->pm.profiles[PM_PROFILE_LOW_MH_IDX].dpms_off_cm_idx = 0; |
rdev->pm.profiles[PM_PROFILE_LOW_MH_IDX].dpms_on_cm_idx = 0; |
/* mid mh */ |
rdev->pm.profiles[PM_PROFILE_MID_MH_IDX].dpms_off_ps_idx = 0; |
rdev->pm.profiles[PM_PROFILE_MID_MH_IDX].dpms_on_ps_idx = rdev->pm.default_power_state_index; |
rdev->pm.profiles[PM_PROFILE_MID_MH_IDX].dpms_off_cm_idx = 0; |
rdev->pm.profiles[PM_PROFILE_MID_MH_IDX].dpms_on_cm_idx = 0; |
/* high mh */ |
rdev->pm.profiles[PM_PROFILE_HIGH_MH_IDX].dpms_off_ps_idx = 0; |
rdev->pm.profiles[PM_PROFILE_HIGH_MH_IDX].dpms_on_ps_idx = rdev->pm.default_power_state_index; |
rdev->pm.profiles[PM_PROFILE_HIGH_MH_IDX].dpms_off_cm_idx = 0; |
rdev->pm.profiles[PM_PROFILE_HIGH_MH_IDX].dpms_on_cm_idx = 0; |
} |
static void r420_set_reg_safe(struct radeon_device *rdev) |
{ |
rdev->config.r300.reg_safe_bm = r420_reg_safe_bm; |
226,6 → 265,12 |
} |
/* Enable IRQ */ |
if (!rdev->irq.installed) { |
r = radeon_irq_kms_init(rdev); |
if (r) |
return r; |
} |
r100_irq_set(rdev); |
rdev->config.r300.hdp_cntl = RREG32(RADEON_HOST_PATH_CNTL); |
/* 1M ring buffer */ |
305,10 → 350,6 |
if (r) { |
return r; |
} |
r = radeon_irq_kms_init(rdev); |
if (r) { |
return r; |
} |
/* Memory manager */ |
r = radeon_bo_init(rdev); |
if (r) { |
/drivers/video/drm/radeon/r500_reg.h |
---|
355,9 → 355,12 |
# define AVIVO_D1CRTC_V_BLANK (1 << 0) |
#define AVIVO_D1CRTC_STATUS_POSITION 0x60a0 |
#define AVIVO_D1CRTC_FRAME_COUNT 0x60a4 |
#define AVIVO_D1CRTC_STATUS_HV_COUNT 0x60ac |
#define AVIVO_D1CRTC_STEREO_CONTROL 0x60c4 |
#define AVIVO_D1MODE_MASTER_UPDATE_LOCK 0x60e0 |
#define AVIVO_D1MODE_MASTER_UPDATE_MODE 0x60e4 |
#define AVIVO_D1CRTC_UPDATE_LOCK 0x60e8 |
/* master controls */ |
#define AVIVO_DC_CRTC_MASTER_EN 0x60f8 |
/drivers/video/drm/radeon/r520.c |
---|
194,6 → 194,12 |
} |
/* Enable IRQ */ |
if (!rdev->irq.installed) { |
r = radeon_irq_kms_init(rdev); |
if (r) |
return r; |
} |
rs600_irq_set(rdev); |
rdev->config.r300.hdp_cntl = RREG32(RADEON_HOST_PATH_CNTL); |
/* 1M ring buffer */ |
269,9 → 275,6 |
r = radeon_fence_driver_init(rdev); |
if (r) |
return r; |
r = radeon_irq_kms_init(rdev); |
if (r) |
return r; |
/* Memory manager */ |
r = radeon_bo_init(rdev); |
if (r) |
/drivers/video/drm/radeon/r600.c |
---|
93,6 → 93,12 |
MODULE_FIRMWARE("radeon/SUMO2_pfp.bin"); |
MODULE_FIRMWARE("radeon/SUMO2_me.bin"); |
static const u32 crtc_offsets[2] = |
{ |
0, |
AVIVO_D2CRTC_H_TOTAL - AVIVO_D1CRTC_H_TOTAL |
}; |
int r600_debugfs_mc_info_init(struct radeon_device *rdev); |
/* r600,rv610,rv630,rv620,rv635,rv670 */ |
102,6 → 108,19 |
void r600_irq_disable(struct radeon_device *rdev); |
static void r600_pcie_gen2_enable(struct radeon_device *rdev); |
/** |
* r600_get_xclk - get the xclk |
* |
* @rdev: radeon_device pointer |
* |
* Returns the reference clock used by the gfx engine |
* (r6xx, IGPs, APUs). |
*/ |
u32 r600_get_xclk(struct radeon_device *rdev) |
{ |
return rdev->clock.spll.reference_freq; |
} |
/* get temperature in millidegrees */ |
int rv6xx_get_temp(struct radeon_device *rdev) |
{ |
598,6 → 617,24 |
return -1; |
} |
uint32_t rs780_mc_rreg(struct radeon_device *rdev, uint32_t reg) |
{ |
uint32_t r; |
WREG32(R_0028F8_MC_INDEX, S_0028F8_MC_IND_ADDR(reg)); |
r = RREG32(R_0028FC_MC_DATA); |
WREG32(R_0028F8_MC_INDEX, ~C_0028F8_MC_IND_ADDR); |
return r; |
} |
void rs780_mc_wreg(struct radeon_device *rdev, uint32_t reg, uint32_t v) |
{ |
WREG32(R_0028F8_MC_INDEX, S_0028F8_MC_IND_ADDR(reg) | |
S_0028F8_MC_IND_WR_EN(1)); |
WREG32(R_0028FC_MC_DATA, v); |
WREG32(R_0028F8_MC_INDEX, 0x7F); |
} |
static void r600_mc_program(struct radeon_device *rdev) |
{ |
struct rv515_mc_save save; |
697,7 → 734,7 |
} |
if (rdev->flags & RADEON_IS_AGP) { |
size_bf = mc->gtt_start; |
size_af = 0xFFFFFFFF - mc->gtt_end; |
size_af = mc->mc_mask - mc->gtt_end; |
if (size_bf > size_af) { |
if (mc->mc_vram_size > size_bf) { |
dev_warn(rdev->dev, "limiting VRAM\n"); |
733,6 → 770,8 |
{ |
u32 tmp; |
int chansize, numchan; |
uint32_t h_addr, l_addr; |
unsigned long long k8_addr; |
/* Get VRAM informations */ |
rdev->mc.vram_is_ddr = true; |
773,7 → 812,30 |
if (rdev->flags & RADEON_IS_IGP) { |
rs690_pm_info(rdev); |
rdev->mc.igp_sideport_enabled = radeon_atombios_sideport_present(rdev); |
if (rdev->family == CHIP_RS780 || rdev->family == CHIP_RS880) { |
/* Use K8 direct mapping for fast fb access. */ |
rdev->fastfb_working = false; |
h_addr = G_000012_K8_ADDR_EXT(RREG32_MC(R_000012_MC_MISC_UMA_CNTL)); |
l_addr = RREG32_MC(R_000011_K8_FB_LOCATION); |
k8_addr = ((unsigned long long)h_addr) << 32 | l_addr; |
#if defined(CONFIG_X86_32) && !defined(CONFIG_X86_PAE) |
if (k8_addr + rdev->mc.visible_vram_size < 0x100000000ULL) |
#endif |
{ |
/* FastFB shall be used with UMA memory. Here it is simply disabled when sideport |
* memory is present. |
*/ |
if (rdev->mc.igp_sideport_enabled == false && radeon_fastfb == 1) { |
DRM_INFO("Direct mapping: aper base at 0x%llx, replaced by direct mapping base 0x%llx.\n", |
(unsigned long long)rdev->mc.aper_base, k8_addr); |
rdev->mc.aper_base = (resource_size_t)k8_addr; |
rdev->fastfb_working = true; |
} |
} |
} |
} |
radeon_update_bandwidth_info(rdev); |
return 0; |
} |
808,33 → 870,37 |
return r; |
} |
/* We doesn't check that the GPU really needs a reset we simply do the |
* reset, it's up to the caller to determine if the GPU needs one. We |
* might add an helper function to check that. |
*/ |
static void r600_gpu_soft_reset_gfx(struct radeon_device *rdev) |
void r600_vram_scratch_fini(struct radeon_device *rdev) |
{ |
u32 grbm_busy_mask = S_008010_VC_BUSY(1) | S_008010_VGT_BUSY_NO_DMA(1) | |
S_008010_VGT_BUSY(1) | S_008010_TA03_BUSY(1) | |
S_008010_TC_BUSY(1) | S_008010_SX_BUSY(1) | |
S_008010_SH_BUSY(1) | S_008010_SPI03_BUSY(1) | |
S_008010_SMX_BUSY(1) | S_008010_SC_BUSY(1) | |
S_008010_PA_BUSY(1) | S_008010_DB03_BUSY(1) | |
S_008010_CR_BUSY(1) | S_008010_CB03_BUSY(1) | |
S_008010_GUI_ACTIVE(1); |
u32 grbm2_busy_mask = S_008014_SPI0_BUSY(1) | S_008014_SPI1_BUSY(1) | |
S_008014_SPI2_BUSY(1) | S_008014_SPI3_BUSY(1) | |
S_008014_TA0_BUSY(1) | S_008014_TA1_BUSY(1) | |
S_008014_TA2_BUSY(1) | S_008014_TA3_BUSY(1) | |
S_008014_DB0_BUSY(1) | S_008014_DB1_BUSY(1) | |
S_008014_DB2_BUSY(1) | S_008014_DB3_BUSY(1) | |
S_008014_CB0_BUSY(1) | S_008014_CB1_BUSY(1) | |
S_008014_CB2_BUSY(1) | S_008014_CB3_BUSY(1); |
u32 tmp; |
int r; |
if (!(RREG32(GRBM_STATUS) & GUI_ACTIVE)) |
if (rdev->vram_scratch.robj == NULL) { |
return; |
} |
r = radeon_bo_reserve(rdev->vram_scratch.robj, false); |
if (likely(r == 0)) { |
radeon_bo_kunmap(rdev->vram_scratch.robj); |
radeon_bo_unpin(rdev->vram_scratch.robj); |
radeon_bo_unreserve(rdev->vram_scratch.robj); |
} |
radeon_bo_unref(&rdev->vram_scratch.robj); |
} |
void r600_set_bios_scratch_engine_hung(struct radeon_device *rdev, bool hung) |
{ |
u32 tmp = RREG32(R600_BIOS_3_SCRATCH); |
if (hung) |
tmp |= ATOM_S3_ASIC_GUI_ENGINE_HUNG; |
else |
tmp &= ~ATOM_S3_ASIC_GUI_ENGINE_HUNG; |
WREG32(R600_BIOS_3_SCRATCH, tmp); |
} |
static void r600_print_gpu_status_regs(struct radeon_device *rdev) |
{ |
dev_info(rdev->dev, " R_008010_GRBM_STATUS = 0x%08X\n", |
RREG32(R_008010_GRBM_STATUS)); |
dev_info(rdev->dev, " R_008014_GRBM_STATUS2 = 0x%08X\n", |
849,14 → 915,159 |
RREG32(CP_BUSY_STAT)); |
dev_info(rdev->dev, " R_008680_CP_STAT = 0x%08X\n", |
RREG32(CP_STAT)); |
dev_info(rdev->dev, " R_00D034_DMA_STATUS_REG = 0x%08X\n", |
RREG32(DMA_STATUS_REG)); |
} |
static bool r600_is_display_hung(struct radeon_device *rdev) |
{ |
u32 crtc_hung = 0; |
u32 crtc_status[2]; |
u32 i, j, tmp; |
for (i = 0; i < rdev->num_crtc; i++) { |
if (RREG32(AVIVO_D1CRTC_CONTROL + crtc_offsets[i]) & AVIVO_CRTC_EN) { |
crtc_status[i] = RREG32(AVIVO_D1CRTC_STATUS_HV_COUNT + crtc_offsets[i]); |
crtc_hung |= (1 << i); |
} |
} |
for (j = 0; j < 10; j++) { |
for (i = 0; i < rdev->num_crtc; i++) { |
if (crtc_hung & (1 << i)) { |
tmp = RREG32(AVIVO_D1CRTC_STATUS_HV_COUNT + crtc_offsets[i]); |
if (tmp != crtc_status[i]) |
crtc_hung &= ~(1 << i); |
} |
} |
if (crtc_hung == 0) |
return false; |
udelay(100); |
} |
return true; |
} |
static u32 r600_gpu_check_soft_reset(struct radeon_device *rdev) |
{ |
u32 reset_mask = 0; |
u32 tmp; |
/* GRBM_STATUS */ |
tmp = RREG32(R_008010_GRBM_STATUS); |
if (rdev->family >= CHIP_RV770) { |
if (G_008010_PA_BUSY(tmp) | G_008010_SC_BUSY(tmp) | |
G_008010_SH_BUSY(tmp) | G_008010_SX_BUSY(tmp) | |
G_008010_TA_BUSY(tmp) | G_008010_VGT_BUSY(tmp) | |
G_008010_DB03_BUSY(tmp) | G_008010_CB03_BUSY(tmp) | |
G_008010_SPI03_BUSY(tmp) | G_008010_VGT_BUSY_NO_DMA(tmp)) |
reset_mask |= RADEON_RESET_GFX; |
} else { |
if (G_008010_PA_BUSY(tmp) | G_008010_SC_BUSY(tmp) | |
G_008010_SH_BUSY(tmp) | G_008010_SX_BUSY(tmp) | |
G_008010_TA03_BUSY(tmp) | G_008010_VGT_BUSY(tmp) | |
G_008010_DB03_BUSY(tmp) | G_008010_CB03_BUSY(tmp) | |
G_008010_SPI03_BUSY(tmp) | G_008010_VGT_BUSY_NO_DMA(tmp)) |
reset_mask |= RADEON_RESET_GFX; |
} |
if (G_008010_CF_RQ_PENDING(tmp) | G_008010_PF_RQ_PENDING(tmp) | |
G_008010_CP_BUSY(tmp) | G_008010_CP_COHERENCY_BUSY(tmp)) |
reset_mask |= RADEON_RESET_CP; |
if (G_008010_GRBM_EE_BUSY(tmp)) |
reset_mask |= RADEON_RESET_GRBM | RADEON_RESET_GFX | RADEON_RESET_CP; |
/* DMA_STATUS_REG */ |
tmp = RREG32(DMA_STATUS_REG); |
if (!(tmp & DMA_IDLE)) |
reset_mask |= RADEON_RESET_DMA; |
/* SRBM_STATUS */ |
tmp = RREG32(R_000E50_SRBM_STATUS); |
if (G_000E50_RLC_RQ_PENDING(tmp) | G_000E50_RLC_BUSY(tmp)) |
reset_mask |= RADEON_RESET_RLC; |
if (G_000E50_IH_BUSY(tmp)) |
reset_mask |= RADEON_RESET_IH; |
if (G_000E50_SEM_BUSY(tmp)) |
reset_mask |= RADEON_RESET_SEM; |
if (G_000E50_GRBM_RQ_PENDING(tmp)) |
reset_mask |= RADEON_RESET_GRBM; |
if (G_000E50_VMC_BUSY(tmp)) |
reset_mask |= RADEON_RESET_VMC; |
if (G_000E50_MCB_BUSY(tmp) | G_000E50_MCDZ_BUSY(tmp) | |
G_000E50_MCDY_BUSY(tmp) | G_000E50_MCDX_BUSY(tmp) | |
G_000E50_MCDW_BUSY(tmp)) |
reset_mask |= RADEON_RESET_MC; |
if (r600_is_display_hung(rdev)) |
reset_mask |= RADEON_RESET_DISPLAY; |
/* Skip MC reset as it's mostly likely not hung, just busy */ |
if (reset_mask & RADEON_RESET_MC) { |
DRM_DEBUG("MC busy: 0x%08X, clearing.\n", reset_mask); |
reset_mask &= ~RADEON_RESET_MC; |
} |
return reset_mask; |
} |
static void r600_gpu_soft_reset(struct radeon_device *rdev, u32 reset_mask) |
{ |
struct rv515_mc_save save; |
u32 grbm_soft_reset = 0, srbm_soft_reset = 0; |
u32 tmp; |
if (reset_mask == 0) |
return; |
dev_info(rdev->dev, "GPU softreset: 0x%08X\n", reset_mask); |
r600_print_gpu_status_regs(rdev); |
/* Disable CP parsing/prefetching */ |
if (rdev->family >= CHIP_RV770) |
WREG32(R_0086D8_CP_ME_CNTL, S_0086D8_CP_ME_HALT(1) | S_0086D8_CP_PFP_HALT(1)); |
else |
WREG32(R_0086D8_CP_ME_CNTL, S_0086D8_CP_ME_HALT(1)); |
/* Check if any of the rendering block is busy and reset it */ |
if ((RREG32(R_008010_GRBM_STATUS) & grbm_busy_mask) || |
(RREG32(R_008014_GRBM_STATUS2) & grbm2_busy_mask)) { |
tmp = S_008020_SOFT_RESET_CR(1) | |
/* disable the RLC */ |
WREG32(RLC_CNTL, 0); |
if (reset_mask & RADEON_RESET_DMA) { |
/* Disable DMA */ |
tmp = RREG32(DMA_RB_CNTL); |
tmp &= ~DMA_RB_ENABLE; |
WREG32(DMA_RB_CNTL, tmp); |
} |
mdelay(50); |
rv515_mc_stop(rdev, &save); |
if (r600_mc_wait_for_idle(rdev)) { |
dev_warn(rdev->dev, "Wait for MC idle timedout !\n"); |
} |
if (reset_mask & (RADEON_RESET_GFX | RADEON_RESET_COMPUTE)) { |
if (rdev->family >= CHIP_RV770) |
grbm_soft_reset |= S_008020_SOFT_RESET_DB(1) | |
S_008020_SOFT_RESET_CB(1) | |
S_008020_SOFT_RESET_PA(1) | |
S_008020_SOFT_RESET_SC(1) | |
S_008020_SOFT_RESET_SPI(1) | |
S_008020_SOFT_RESET_SX(1) | |
S_008020_SOFT_RESET_SH(1) | |
S_008020_SOFT_RESET_TC(1) | |
S_008020_SOFT_RESET_TA(1) | |
S_008020_SOFT_RESET_VC(1) | |
S_008020_SOFT_RESET_VGT(1); |
else |
grbm_soft_reset |= S_008020_SOFT_RESET_CR(1) | |
S_008020_SOFT_RESET_DB(1) | |
S_008020_SOFT_RESET_CB(1) | |
S_008020_SOFT_RESET_PA(1) | |
869,102 → 1080,114 |
S_008020_SOFT_RESET_TA(1) | |
S_008020_SOFT_RESET_VC(1) | |
S_008020_SOFT_RESET_VGT(1); |
dev_info(rdev->dev, " R_008020_GRBM_SOFT_RESET=0x%08X\n", tmp); |
WREG32(R_008020_GRBM_SOFT_RESET, tmp); |
RREG32(R_008020_GRBM_SOFT_RESET); |
mdelay(15); |
WREG32(R_008020_GRBM_SOFT_RESET, 0); |
} |
/* Reset CP (we always reset CP) */ |
tmp = S_008020_SOFT_RESET_CP(1); |
dev_info(rdev->dev, "R_008020_GRBM_SOFT_RESET=0x%08X\n", tmp); |
WREG32(R_008020_GRBM_SOFT_RESET, tmp); |
RREG32(R_008020_GRBM_SOFT_RESET); |
mdelay(15); |
WREG32(R_008020_GRBM_SOFT_RESET, 0); |
dev_info(rdev->dev, " R_008010_GRBM_STATUS = 0x%08X\n", |
RREG32(R_008010_GRBM_STATUS)); |
dev_info(rdev->dev, " R_008014_GRBM_STATUS2 = 0x%08X\n", |
RREG32(R_008014_GRBM_STATUS2)); |
dev_info(rdev->dev, " R_000E50_SRBM_STATUS = 0x%08X\n", |
RREG32(R_000E50_SRBM_STATUS)); |
dev_info(rdev->dev, " R_008674_CP_STALLED_STAT1 = 0x%08X\n", |
RREG32(CP_STALLED_STAT1)); |
dev_info(rdev->dev, " R_008678_CP_STALLED_STAT2 = 0x%08X\n", |
RREG32(CP_STALLED_STAT2)); |
dev_info(rdev->dev, " R_00867C_CP_BUSY_STAT = 0x%08X\n", |
RREG32(CP_BUSY_STAT)); |
dev_info(rdev->dev, " R_008680_CP_STAT = 0x%08X\n", |
RREG32(CP_STAT)); |
if (reset_mask & RADEON_RESET_CP) { |
grbm_soft_reset |= S_008020_SOFT_RESET_CP(1) | |
S_008020_SOFT_RESET_VGT(1); |
srbm_soft_reset |= S_000E60_SOFT_RESET_GRBM(1); |
} |
static void r600_gpu_soft_reset_dma(struct radeon_device *rdev) |
{ |
u32 tmp; |
if (reset_mask & RADEON_RESET_DMA) { |
if (rdev->family >= CHIP_RV770) |
srbm_soft_reset |= RV770_SOFT_RESET_DMA; |
else |
srbm_soft_reset |= SOFT_RESET_DMA; |
} |
if (RREG32(DMA_STATUS_REG) & DMA_IDLE) |
return; |
if (reset_mask & RADEON_RESET_RLC) |
srbm_soft_reset |= S_000E60_SOFT_RESET_RLC(1); |
dev_info(rdev->dev, " R_00D034_DMA_STATUS_REG = 0x%08X\n", |
RREG32(DMA_STATUS_REG)); |
if (reset_mask & RADEON_RESET_SEM) |
srbm_soft_reset |= S_000E60_SOFT_RESET_SEM(1); |
/* Disable DMA */ |
tmp = RREG32(DMA_RB_CNTL); |
tmp &= ~DMA_RB_ENABLE; |
WREG32(DMA_RB_CNTL, tmp); |
if (reset_mask & RADEON_RESET_IH) |
srbm_soft_reset |= S_000E60_SOFT_RESET_IH(1); |
/* Reset dma */ |
if (rdev->family >= CHIP_RV770) |
WREG32(SRBM_SOFT_RESET, RV770_SOFT_RESET_DMA); |
else |
WREG32(SRBM_SOFT_RESET, SOFT_RESET_DMA); |
RREG32(SRBM_SOFT_RESET); |
udelay(50); |
WREG32(SRBM_SOFT_RESET, 0); |
if (reset_mask & RADEON_RESET_GRBM) |
srbm_soft_reset |= S_000E60_SOFT_RESET_GRBM(1); |
dev_info(rdev->dev, " R_00D034_DMA_STATUS_REG = 0x%08X\n", |
RREG32(DMA_STATUS_REG)); |
if (!(rdev->flags & RADEON_IS_IGP)) { |
if (reset_mask & RADEON_RESET_MC) |
srbm_soft_reset |= S_000E60_SOFT_RESET_MC(1); |
} |
static int r600_gpu_soft_reset(struct radeon_device *rdev, u32 reset_mask) |
{ |
struct rv515_mc_save save; |
if (reset_mask & RADEON_RESET_VMC) |
srbm_soft_reset |= S_000E60_SOFT_RESET_VMC(1); |
if (reset_mask == 0) |
return 0; |
if (grbm_soft_reset) { |
tmp = RREG32(R_008020_GRBM_SOFT_RESET); |
tmp |= grbm_soft_reset; |
dev_info(rdev->dev, "R_008020_GRBM_SOFT_RESET=0x%08X\n", tmp); |
WREG32(R_008020_GRBM_SOFT_RESET, tmp); |
tmp = RREG32(R_008020_GRBM_SOFT_RESET); |
dev_info(rdev->dev, "GPU softreset: 0x%08X\n", reset_mask); |
udelay(50); |
rv515_mc_stop(rdev, &save); |
if (r600_mc_wait_for_idle(rdev)) { |
dev_warn(rdev->dev, "Wait for MC idle timedout !\n"); |
tmp &= ~grbm_soft_reset; |
WREG32(R_008020_GRBM_SOFT_RESET, tmp); |
tmp = RREG32(R_008020_GRBM_SOFT_RESET); |
} |
if (reset_mask & (RADEON_RESET_GFX | RADEON_RESET_COMPUTE)) |
r600_gpu_soft_reset_gfx(rdev); |
if (srbm_soft_reset) { |
tmp = RREG32(SRBM_SOFT_RESET); |
tmp |= srbm_soft_reset; |
dev_info(rdev->dev, "SRBM_SOFT_RESET=0x%08X\n", tmp); |
WREG32(SRBM_SOFT_RESET, tmp); |
tmp = RREG32(SRBM_SOFT_RESET); |
if (reset_mask & RADEON_RESET_DMA) |
r600_gpu_soft_reset_dma(rdev); |
udelay(50); |
tmp &= ~srbm_soft_reset; |
WREG32(SRBM_SOFT_RESET, tmp); |
tmp = RREG32(SRBM_SOFT_RESET); |
} |
/* Wait a little for things to settle down */ |
mdelay(1); |
rv515_mc_resume(rdev, &save); |
udelay(50); |
r600_print_gpu_status_regs(rdev); |
} |
int r600_asic_reset(struct radeon_device *rdev) |
{ |
u32 reset_mask; |
reset_mask = r600_gpu_check_soft_reset(rdev); |
if (reset_mask) |
r600_set_bios_scratch_engine_hung(rdev, true); |
r600_gpu_soft_reset(rdev, reset_mask); |
reset_mask = r600_gpu_check_soft_reset(rdev); |
if (!reset_mask) |
r600_set_bios_scratch_engine_hung(rdev, false); |
return 0; |
} |
bool r600_gpu_is_lockup(struct radeon_device *rdev, struct radeon_ring *ring) |
/** |
* r600_gfx_is_lockup - Check if the GFX engine is locked up |
* |
* @rdev: radeon_device pointer |
* @ring: radeon_ring structure holding ring information |
* |
* Check if the GFX engine is locked up. |
* Returns true if the engine appears to be locked up, false if not. |
*/ |
bool r600_gfx_is_lockup(struct radeon_device *rdev, struct radeon_ring *ring) |
{ |
u32 srbm_status; |
u32 grbm_status; |
u32 grbm_status2; |
u32 reset_mask = r600_gpu_check_soft_reset(rdev); |
srbm_status = RREG32(R_000E50_SRBM_STATUS); |
grbm_status = RREG32(R_008010_GRBM_STATUS); |
grbm_status2 = RREG32(R_008014_GRBM_STATUS2); |
if (!G_008010_GUI_ACTIVE(grbm_status)) { |
if (!(reset_mask & (RADEON_RESET_GFX | |
RADEON_RESET_COMPUTE | |
RADEON_RESET_CP))) { |
radeon_ring_lockup_update(ring); |
return false; |
} |
979,15 → 1202,14 |
* @rdev: radeon_device pointer |
* @ring: radeon_ring structure holding ring information |
* |
* Check if the async DMA engine is locked up (r6xx-evergreen). |
* Check if the async DMA engine is locked up. |
* Returns true if the engine appears to be locked up, false if not. |
*/ |
bool r600_dma_is_lockup(struct radeon_device *rdev, struct radeon_ring *ring) |
{ |
u32 dma_status_reg; |
u32 reset_mask = r600_gpu_check_soft_reset(rdev); |
dma_status_reg = RREG32(DMA_STATUS_REG); |
if (dma_status_reg & DMA_IDLE) { |
if (!(reset_mask & RADEON_RESET_DMA)) { |
radeon_ring_lockup_update(ring); |
return false; |
} |
996,13 → 1218,6 |
return radeon_ring_test_lockup(rdev, ring); |
} |
int r600_asic_reset(struct radeon_device *rdev) |
{ |
return r600_gpu_soft_reset(rdev, (RADEON_RESET_GFX | |
RADEON_RESET_COMPUTE | |
RADEON_RESET_DMA)); |
} |
u32 r6xx_remap_render_backend(struct radeon_device *rdev, |
u32 tiling_pipe_num, |
u32 max_rb_num, |
1010,12 → 1225,15 |
u32 disabled_rb_mask) |
{ |
u32 rendering_pipe_num, rb_num_width, req_rb_num; |
u32 pipe_rb_ratio, pipe_rb_remain; |
u32 pipe_rb_ratio, pipe_rb_remain, tmp; |
u32 data = 0, mask = 1 << (max_rb_num - 1); |
unsigned i, j; |
/* mask out the RBs that don't exist on that asic */ |
disabled_rb_mask |= (0xff << max_rb_num) & 0xff; |
tmp = disabled_rb_mask | ((0xff << max_rb_num) & 0xff); |
/* make sure at least one RB is available */ |
if ((tmp & 0xff) != 0xff) |
disabled_rb_mask = tmp; |
rendering_pipe_num = 1 << tiling_pipe_num; |
req_rb_num = total_max_rb_num - r600_count_pipe_bits(disabled_rb_mask); |
1861,7 → 2079,7 |
int r600_dma_resume(struct radeon_device *rdev) |
{ |
struct radeon_ring *ring = &rdev->ring[R600_RING_TYPE_DMA_INDEX]; |
u32 rb_cntl, dma_cntl; |
u32 rb_cntl, dma_cntl, ib_cntl; |
u32 rb_bufsz; |
int r; |
1901,7 → 2119,11 |
WREG32(DMA_RB_BASE, ring->gpu_addr >> 8); |
/* enable DMA IBs */ |
WREG32(DMA_IB_CNTL, DMA_IB_ENABLE); |
ib_cntl = DMA_IB_ENABLE; |
#ifdef __BIG_ENDIAN |
ib_cntl |= DMA_IB_SWAP_ENABLE; |
#endif |
WREG32(DMA_IB_CNTL, ib_cntl); |
dma_cntl = RREG32(DMA_CNTL); |
dma_cntl &= ~CTXEMPTY_INT_ENABLE; |
1944,6 → 2166,200 |
} |
/* |
* UVD |
*/ |
int r600_uvd_rbc_start(struct radeon_device *rdev) |
{ |
struct radeon_ring *ring = &rdev->ring[R600_RING_TYPE_UVD_INDEX]; |
uint64_t rptr_addr; |
uint32_t rb_bufsz, tmp; |
int r; |
rptr_addr = rdev->wb.gpu_addr + R600_WB_UVD_RPTR_OFFSET; |
if (upper_32_bits(rptr_addr) != upper_32_bits(ring->gpu_addr)) { |
DRM_ERROR("UVD ring and rptr not in the same 4GB segment!\n"); |
return -EINVAL; |
} |
/* force RBC into idle state */ |
WREG32(UVD_RBC_RB_CNTL, 0x11010101); |
/* Set the write pointer delay */ |
WREG32(UVD_RBC_RB_WPTR_CNTL, 0); |
/* set the wb address */ |
WREG32(UVD_RBC_RB_RPTR_ADDR, rptr_addr >> 2); |
/* programm the 4GB memory segment for rptr and ring buffer */ |
WREG32(UVD_LMI_EXT40_ADDR, upper_32_bits(rptr_addr) | |
(0x7 << 16) | (0x1 << 31)); |
/* Initialize the ring buffer's read and write pointers */ |
WREG32(UVD_RBC_RB_RPTR, 0x0); |
ring->wptr = ring->rptr = RREG32(UVD_RBC_RB_RPTR); |
WREG32(UVD_RBC_RB_WPTR, ring->wptr); |
/* set the ring address */ |
WREG32(UVD_RBC_RB_BASE, ring->gpu_addr); |
/* Set ring buffer size */ |
rb_bufsz = drm_order(ring->ring_size); |
rb_bufsz = (0x1 << 8) | rb_bufsz; |
WREG32(UVD_RBC_RB_CNTL, rb_bufsz); |
ring->ready = true; |
r = radeon_ring_test(rdev, R600_RING_TYPE_UVD_INDEX, ring); |
if (r) { |
ring->ready = false; |
return r; |
} |
r = radeon_ring_lock(rdev, ring, 10); |
if (r) { |
DRM_ERROR("radeon: ring failed to lock UVD ring (%d).\n", r); |
return r; |
} |
tmp = PACKET0(UVD_SEMA_WAIT_FAULT_TIMEOUT_CNTL, 0); |
radeon_ring_write(ring, tmp); |
radeon_ring_write(ring, 0xFFFFF); |
tmp = PACKET0(UVD_SEMA_WAIT_INCOMPLETE_TIMEOUT_CNTL, 0); |
radeon_ring_write(ring, tmp); |
radeon_ring_write(ring, 0xFFFFF); |
tmp = PACKET0(UVD_SEMA_SIGNAL_INCOMPLETE_TIMEOUT_CNTL, 0); |
radeon_ring_write(ring, tmp); |
radeon_ring_write(ring, 0xFFFFF); |
/* Clear timeout status bits */ |
radeon_ring_write(ring, PACKET0(UVD_SEMA_TIMEOUT_STATUS, 0)); |
radeon_ring_write(ring, 0x8); |
radeon_ring_write(ring, PACKET0(UVD_SEMA_CNTL, 0)); |
radeon_ring_write(ring, 3); |
radeon_ring_unlock_commit(rdev, ring); |
return 0; |
} |
void r600_uvd_rbc_stop(struct radeon_device *rdev) |
{ |
struct radeon_ring *ring = &rdev->ring[R600_RING_TYPE_UVD_INDEX]; |
/* force RBC into idle state */ |
WREG32(UVD_RBC_RB_CNTL, 0x11010101); |
ring->ready = false; |
} |
int r600_uvd_init(struct radeon_device *rdev) |
{ |
int i, j, r; |
/* disable byte swapping */ |
u32 lmi_swap_cntl = 0; |
u32 mp_swap_cntl = 0; |
/* raise clocks while booting up the VCPU */ |
radeon_set_uvd_clocks(rdev, 53300, 40000); |
/* disable clock gating */ |
WREG32(UVD_CGC_GATE, 0); |
/* disable interupt */ |
WREG32_P(UVD_MASTINT_EN, 0, ~(1 << 1)); |
/* put LMI, VCPU, RBC etc... into reset */ |
WREG32(UVD_SOFT_RESET, LMI_SOFT_RESET | VCPU_SOFT_RESET | |
LBSI_SOFT_RESET | RBC_SOFT_RESET | CSM_SOFT_RESET | |
CXW_SOFT_RESET | TAP_SOFT_RESET | LMI_UMC_SOFT_RESET); |
mdelay(5); |
/* take UVD block out of reset */ |
WREG32_P(SRBM_SOFT_RESET, 0, ~SOFT_RESET_UVD); |
mdelay(5); |
/* initialize UVD memory controller */ |
WREG32(UVD_LMI_CTRL, 0x40 | (1 << 8) | (1 << 13) | |
(1 << 21) | (1 << 9) | (1 << 20)); |
#ifdef __BIG_ENDIAN |
/* swap (8 in 32) RB and IB */ |
lmi_swap_cntl = 0xa; |
mp_swap_cntl = 0; |
#endif |
WREG32(UVD_LMI_SWAP_CNTL, lmi_swap_cntl); |
WREG32(UVD_MP_SWAP_CNTL, mp_swap_cntl); |
WREG32(UVD_MPC_SET_MUXA0, 0x40c2040); |
WREG32(UVD_MPC_SET_MUXA1, 0x0); |
WREG32(UVD_MPC_SET_MUXB0, 0x40c2040); |
WREG32(UVD_MPC_SET_MUXB1, 0x0); |
WREG32(UVD_MPC_SET_ALU, 0); |
WREG32(UVD_MPC_SET_MUX, 0x88); |
/* Stall UMC */ |
WREG32_P(UVD_LMI_CTRL2, 1 << 8, ~(1 << 8)); |
WREG32_P(UVD_RB_ARB_CTRL, 1 << 3, ~(1 << 3)); |
/* take all subblocks out of reset, except VCPU */ |
WREG32(UVD_SOFT_RESET, VCPU_SOFT_RESET); |
mdelay(5); |
/* enable VCPU clock */ |
WREG32(UVD_VCPU_CNTL, 1 << 9); |
/* enable UMC */ |
WREG32_P(UVD_LMI_CTRL2, 0, ~(1 << 8)); |
/* boot up the VCPU */ |
WREG32(UVD_SOFT_RESET, 0); |
mdelay(10); |
WREG32_P(UVD_RB_ARB_CTRL, 0, ~(1 << 3)); |
for (i = 0; i < 10; ++i) { |
uint32_t status; |
for (j = 0; j < 100; ++j) { |
status = RREG32(UVD_STATUS); |
if (status & 2) |
break; |
mdelay(10); |
} |
r = 0; |
if (status & 2) |
break; |
DRM_ERROR("UVD not responding, trying to reset the VCPU!!!\n"); |
WREG32_P(UVD_SOFT_RESET, VCPU_SOFT_RESET, ~VCPU_SOFT_RESET); |
mdelay(10); |
WREG32_P(UVD_SOFT_RESET, 0, ~VCPU_SOFT_RESET); |
mdelay(10); |
r = -1; |
} |
if (r) { |
DRM_ERROR("UVD not responding, giving up!!!\n"); |
radeon_set_uvd_clocks(rdev, 0, 0); |
return r; |
} |
/* enable interupt */ |
WREG32_P(UVD_MASTINT_EN, 3<<1, ~(3 << 1)); |
r = r600_uvd_rbc_start(rdev); |
if (!r) |
DRM_INFO("UVD initialized successfully.\n"); |
/* lower clocks again */ |
radeon_set_uvd_clocks(rdev, 0, 0); |
return r; |
} |
/* |
* GPU scratch registers helpers function. |
*/ |
void r600_scratch_init(struct radeon_device *rdev) |
2052,6 → 2468,40 |
return r; |
} |
int r600_uvd_ring_test(struct radeon_device *rdev, struct radeon_ring *ring) |
{ |
uint32_t tmp = 0; |
unsigned i; |
int r; |
WREG32(UVD_CONTEXT_ID, 0xCAFEDEAD); |
r = radeon_ring_lock(rdev, ring, 3); |
if (r) { |
DRM_ERROR("radeon: cp failed to lock ring %d (%d).\n", |
ring->idx, r); |
return r; |
} |
radeon_ring_write(ring, PACKET0(UVD_CONTEXT_ID, 0)); |
radeon_ring_write(ring, 0xDEADBEEF); |
radeon_ring_unlock_commit(rdev, ring); |
for (i = 0; i < rdev->usec_timeout; i++) { |
tmp = RREG32(UVD_CONTEXT_ID); |
if (tmp == 0xDEADBEEF) |
break; |
DRM_UDELAY(1); |
} |
if (i < rdev->usec_timeout) { |
DRM_INFO("ring test on %d succeeded in %d usecs\n", |
ring->idx, i); |
} else { |
DRM_ERROR("radeon: ring %d test failed (0x%08X)\n", |
ring->idx, tmp); |
r = -EINVAL; |
} |
return r; |
} |
/* |
* CP fences/semaphores |
*/ |
2103,6 → 2553,30 |
} |
} |
void r600_uvd_fence_emit(struct radeon_device *rdev, |
struct radeon_fence *fence) |
{ |
struct radeon_ring *ring = &rdev->ring[fence->ring]; |
uint32_t addr = rdev->fence_drv[fence->ring].gpu_addr; |
radeon_ring_write(ring, PACKET0(UVD_CONTEXT_ID, 0)); |
radeon_ring_write(ring, fence->seq); |
radeon_ring_write(ring, PACKET0(UVD_GPCOM_VCPU_DATA0, 0)); |
radeon_ring_write(ring, addr & 0xffffffff); |
radeon_ring_write(ring, PACKET0(UVD_GPCOM_VCPU_DATA1, 0)); |
radeon_ring_write(ring, upper_32_bits(addr) & 0xff); |
radeon_ring_write(ring, PACKET0(UVD_GPCOM_VCPU_CMD, 0)); |
radeon_ring_write(ring, 0); |
radeon_ring_write(ring, PACKET0(UVD_GPCOM_VCPU_DATA0, 0)); |
radeon_ring_write(ring, 0); |
radeon_ring_write(ring, PACKET0(UVD_GPCOM_VCPU_DATA1, 0)); |
radeon_ring_write(ring, 0); |
radeon_ring_write(ring, PACKET0(UVD_GPCOM_VCPU_CMD, 0)); |
radeon_ring_write(ring, 2); |
return; |
} |
void r600_semaphore_ring_emit(struct radeon_device *rdev, |
struct radeon_ring *ring, |
struct radeon_semaphore *semaphore, |
2172,6 → 2646,23 |
radeon_ring_write(ring, upper_32_bits(addr) & 0xff); |
} |
void r600_uvd_semaphore_emit(struct radeon_device *rdev, |
struct radeon_ring *ring, |
struct radeon_semaphore *semaphore, |
bool emit_wait) |
{ |
uint64_t addr = semaphore->gpu_addr; |
radeon_ring_write(ring, PACKET0(UVD_SEMA_ADDR_LOW, 0)); |
radeon_ring_write(ring, (addr >> 3) & 0x000FFFFF); |
radeon_ring_write(ring, PACKET0(UVD_SEMA_ADDR_HIGH, 0)); |
radeon_ring_write(ring, (addr >> 23) & 0x000FFFFF); |
radeon_ring_write(ring, PACKET0(UVD_SEMA_CMD, 0)); |
radeon_ring_write(ring, emit_wait ? 1 : 0); |
} |
int r600_copy_blit(struct radeon_device *rdev, |
uint64_t src_offset, |
uint64_t dst_offset, |
2294,6 → 2785,10 |
} |
} |
r = r600_vram_scratch_init(rdev); |
if (r) |
return r; |
r600_mc_program(rdev); |
if (rdev->flags & RADEON_IS_AGP) { |
r600_agp_enable(rdev); |
2328,6 → 2823,12 |
} |
/* Enable IRQ */ |
if (!rdev->irq.installed) { |
r = radeon_irq_kms_init(rdev); |
if (r) |
return r; |
} |
r = r600_irq_init(rdev); |
if (r) { |
DRM_ERROR("radeon: IH init failed (%d).\n", r); |
2445,10 → 2946,6 |
if (r) |
return r; |
r = radeon_irq_kms_init(rdev); |
if (r) |
return r; |
rdev->ring[RADEON_RING_TYPE_GFX_INDEX].ring_obj = NULL; |
r600_ring_init(rdev, &rdev->ring[RADEON_RING_TYPE_GFX_INDEX], 1024 * 1024); |
2506,6 → 3003,16 |
radeon_ring_write(ring, ib->length_dw); |
} |
void r600_uvd_ib_execute(struct radeon_device *rdev, struct radeon_ib *ib) |
{ |
struct radeon_ring *ring = &rdev->ring[ib->ring]; |
radeon_ring_write(ring, PACKET0(UVD_RBC_IB_BASE, 0)); |
radeon_ring_write(ring, ib->gpu_addr); |
radeon_ring_write(ring, PACKET0(UVD_RBC_IB_SIZE, 0)); |
radeon_ring_write(ring, ib->length_dw); |
} |
int r600_ib_test(struct radeon_device *rdev, struct radeon_ring *ring) |
{ |
struct radeon_ib ib; |
2576,8 → 3083,6 |
void __iomem *ptr = (void *)rdev->vram_scratch.ptr; |
u32 tmp = 0; |
ENTER(); |
if (!ptr) { |
DRM_ERROR("invalid vram scratch pointer\n"); |
return -EINVAL; |
2622,12 → 3127,44 |
r = -EINVAL; |
} |
radeon_ib_free(rdev, &ib); |
return r; |
} |
LEAVE(); |
int r600_uvd_ib_test(struct radeon_device *rdev, struct radeon_ring *ring) |
{ |
struct radeon_fence *fence = NULL; |
int r; |
r = radeon_set_uvd_clocks(rdev, 53300, 40000); |
if (r) { |
DRM_ERROR("radeon: failed to raise UVD clocks (%d).\n", r); |
return r; |
} |
// r = radeon_uvd_get_create_msg(rdev, ring->idx, 1, NULL); |
if (r) { |
DRM_ERROR("radeon: failed to get create msg (%d).\n", r); |
goto error; |
} |
// r = radeon_uvd_get_destroy_msg(rdev, ring->idx, 1, &fence); |
if (r) { |
DRM_ERROR("radeon: failed to get destroy ib (%d).\n", r); |
goto error; |
} |
r = radeon_fence_wait(fence, false); |
if (r) { |
DRM_ERROR("radeon: fence wait failed (%d).\n", r); |
goto error; |
} |
DRM_INFO("ib test on ring %d succeeded\n", ring->idx); |
error: |
radeon_fence_unref(&fence); |
radeon_set_uvd_clocks(rdev, 0, 0); |
return r; |
} |
/** |
* r600_dma_ring_ib_execute - Schedule an IB on the DMA engine |
* |
3283,7 → 3820,7 |
* Note, these are based on r600 and may need to be |
* adjusted or added to on newer asics |
*/ |
#undef DRM_DEBUG |
#define DRM_DEBUG(...) |
int r600_irq_process(struct radeon_device *rdev) |
3545,7 → 4082,7 |
void r600_set_pcie_lanes(struct radeon_device *rdev, int lanes) |
{ |
u32 link_width_cntl, mask, target_reg; |
u32 link_width_cntl, mask; |
if (rdev->flags & RADEON_IS_IGP) |
return; |
3557,7 → 4094,7 |
if (ASIC_IS_X2(rdev)) |
return; |
/* FIXME wait for idle */ |
radeon_gui_idle(rdev); |
switch (lanes) { |
case 0: |
3576,53 → 4113,24 |
mask = RADEON_PCIE_LC_LINK_WIDTH_X8; |
break; |
case 12: |
/* not actually supported */ |
mask = RADEON_PCIE_LC_LINK_WIDTH_X12; |
break; |
case 16: |
default: |
mask = RADEON_PCIE_LC_LINK_WIDTH_X16; |
break; |
default: |
DRM_ERROR("invalid pcie lane request: %d\n", lanes); |
return; |
} |
link_width_cntl = RREG32_PCIE_P(RADEON_PCIE_LC_LINK_WIDTH_CNTL); |
if ((link_width_cntl & RADEON_PCIE_LC_LINK_WIDTH_RD_MASK) == |
(mask << RADEON_PCIE_LC_LINK_WIDTH_RD_SHIFT)) |
return; |
if (link_width_cntl & R600_PCIE_LC_UPCONFIGURE_DIS) |
return; |
link_width_cntl &= ~(RADEON_PCIE_LC_LINK_WIDTH_MASK | |
RADEON_PCIE_LC_RECONFIG_NOW | |
R600_PCIE_LC_RENEGOTIATE_EN | |
link_width_cntl = RREG32_PCIE_PORT(RADEON_PCIE_LC_LINK_WIDTH_CNTL); |
link_width_cntl &= ~RADEON_PCIE_LC_LINK_WIDTH_MASK; |
link_width_cntl |= mask << RADEON_PCIE_LC_LINK_WIDTH_SHIFT; |
link_width_cntl |= (RADEON_PCIE_LC_RECONFIG_NOW | |
R600_PCIE_LC_RECONFIG_ARC_MISSING_ESCAPE); |
link_width_cntl |= mask; |
WREG32_PCIE_P(RADEON_PCIE_LC_LINK_WIDTH_CNTL, link_width_cntl); |
/* some northbridges can renegotiate the link rather than requiring |
* a complete re-config. |
* e.g., AMD 780/790 northbridges (pci ids: 0x5956, 0x5957, 0x5958, etc.) |
*/ |
if (link_width_cntl & R600_PCIE_LC_RENEGOTIATION_SUPPORT) |
link_width_cntl |= R600_PCIE_LC_RENEGOTIATE_EN | R600_PCIE_LC_UPCONFIGURE_SUPPORT; |
else |
link_width_cntl |= R600_PCIE_LC_RECONFIG_ARC_MISSING_ESCAPE; |
WREG32_PCIE_P(RADEON_PCIE_LC_LINK_WIDTH_CNTL, (link_width_cntl | |
RADEON_PCIE_LC_RECONFIG_NOW)); |
if (rdev->family >= CHIP_RV770) |
target_reg = R700_TARGET_AND_CURRENT_PROFILE_INDEX; |
else |
target_reg = R600_TARGET_AND_CURRENT_PROFILE_INDEX; |
/* wait for lane set to complete */ |
link_width_cntl = RREG32(target_reg); |
while (link_width_cntl == 0xffffffff) |
link_width_cntl = RREG32(target_reg); |
WREG32_PCIE_PORT(RADEON_PCIE_LC_LINK_WIDTH_CNTL, link_width_cntl); |
} |
int r600_get_pcie_lanes(struct radeon_device *rdev) |
3639,13 → 4147,11 |
if (ASIC_IS_X2(rdev)) |
return 0; |
/* FIXME wait for idle */ |
radeon_gui_idle(rdev); |
link_width_cntl = RREG32_PCIE_P(RADEON_PCIE_LC_LINK_WIDTH_CNTL); |
link_width_cntl = RREG32_PCIE_PORT(RADEON_PCIE_LC_LINK_WIDTH_CNTL); |
switch ((link_width_cntl & RADEON_PCIE_LC_LINK_WIDTH_RD_MASK) >> RADEON_PCIE_LC_LINK_WIDTH_RD_SHIFT) { |
case RADEON_PCIE_LC_LINK_WIDTH_X0: |
return 0; |
case RADEON_PCIE_LC_LINK_WIDTH_X1: |
return 1; |
case RADEON_PCIE_LC_LINK_WIDTH_X2: |
3654,6 → 4160,10 |
return 4; |
case RADEON_PCIE_LC_LINK_WIDTH_X8: |
return 8; |
case RADEON_PCIE_LC_LINK_WIDTH_X12: |
/* not actually supported */ |
return 12; |
case RADEON_PCIE_LC_LINK_WIDTH_X0: |
case RADEON_PCIE_LC_LINK_WIDTH_X16: |
default: |
return 16; |
3664,8 → 4174,6 |
{ |
u32 link_width_cntl, lanes, speed_cntl, training_cntl, tmp; |
u16 link_cntl2; |
u32 mask; |
int ret; |
if (radeon_pcie_gen2 == 0) |
return; |
3684,14 → 4192,11 |
if (rdev->family <= CHIP_R600) |
return; |
ret = drm_pcie_get_speed_cap_mask(rdev->ddev, &mask); |
if (ret != 0) |
if ((rdev->pdev->bus->max_bus_speed != PCIE_SPEED_5_0GT) && |
(rdev->pdev->bus->max_bus_speed != PCIE_SPEED_8_0GT)) |
return; |
if (!(mask & DRM_PCIE_SPEED_50)) |
return; |
speed_cntl = RREG32_PCIE_P(PCIE_LC_SPEED_CNTL); |
speed_cntl = RREG32_PCIE_PORT(PCIE_LC_SPEED_CNTL); |
if (speed_cntl & LC_CURRENT_DATA_RATE) { |
DRM_INFO("PCIE gen 2 link speeds already enabled\n"); |
return; |
3704,23 → 4209,23 |
(rdev->family == CHIP_RV620) || |
(rdev->family == CHIP_RV635)) { |
/* advertise upconfig capability */ |
link_width_cntl = RREG32_PCIE_P(PCIE_LC_LINK_WIDTH_CNTL); |
link_width_cntl = RREG32_PCIE_PORT(PCIE_LC_LINK_WIDTH_CNTL); |
link_width_cntl &= ~LC_UPCONFIGURE_DIS; |
WREG32_PCIE_P(PCIE_LC_LINK_WIDTH_CNTL, link_width_cntl); |
link_width_cntl = RREG32_PCIE_P(PCIE_LC_LINK_WIDTH_CNTL); |
WREG32_PCIE_PORT(PCIE_LC_LINK_WIDTH_CNTL, link_width_cntl); |
link_width_cntl = RREG32_PCIE_PORT(PCIE_LC_LINK_WIDTH_CNTL); |
if (link_width_cntl & LC_RENEGOTIATION_SUPPORT) { |
lanes = (link_width_cntl & LC_LINK_WIDTH_RD_MASK) >> LC_LINK_WIDTH_RD_SHIFT; |
link_width_cntl &= ~(LC_LINK_WIDTH_MASK | |
LC_RECONFIG_ARC_MISSING_ESCAPE); |
link_width_cntl |= lanes | LC_RECONFIG_NOW | LC_RENEGOTIATE_EN; |
WREG32_PCIE_P(PCIE_LC_LINK_WIDTH_CNTL, link_width_cntl); |
WREG32_PCIE_PORT(PCIE_LC_LINK_WIDTH_CNTL, link_width_cntl); |
} else { |
link_width_cntl |= LC_UPCONFIGURE_DIS; |
WREG32_PCIE_P(PCIE_LC_LINK_WIDTH_CNTL, link_width_cntl); |
WREG32_PCIE_PORT(PCIE_LC_LINK_WIDTH_CNTL, link_width_cntl); |
} |
} |
speed_cntl = RREG32_PCIE_P(PCIE_LC_SPEED_CNTL); |
speed_cntl = RREG32_PCIE_PORT(PCIE_LC_SPEED_CNTL); |
if ((speed_cntl & LC_OTHER_SIDE_EVER_SENT_GEN2) && |
(speed_cntl & LC_OTHER_SIDE_SUPPORTS_GEN2)) { |
3741,7 → 4246,7 |
speed_cntl &= ~LC_VOLTAGE_TIMER_SEL_MASK; |
speed_cntl &= ~LC_FORCE_DIS_HW_SPEED_CHANGE; |
speed_cntl |= LC_FORCE_EN_HW_SPEED_CHANGE; |
WREG32_PCIE_P(PCIE_LC_SPEED_CNTL, speed_cntl); |
WREG32_PCIE_PORT(PCIE_LC_SPEED_CNTL, speed_cntl); |
tmp = RREG32(0x541c); |
WREG32(0x541c, tmp | 0x8); |
3755,32 → 4260,32 |
if ((rdev->family == CHIP_RV670) || |
(rdev->family == CHIP_RV620) || |
(rdev->family == CHIP_RV635)) { |
training_cntl = RREG32_PCIE_P(PCIE_LC_TRAINING_CNTL); |
training_cntl = RREG32_PCIE_PORT(PCIE_LC_TRAINING_CNTL); |
training_cntl &= ~LC_POINT_7_PLUS_EN; |
WREG32_PCIE_P(PCIE_LC_TRAINING_CNTL, training_cntl); |
WREG32_PCIE_PORT(PCIE_LC_TRAINING_CNTL, training_cntl); |
} else { |
speed_cntl = RREG32_PCIE_P(PCIE_LC_SPEED_CNTL); |
speed_cntl = RREG32_PCIE_PORT(PCIE_LC_SPEED_CNTL); |
speed_cntl &= ~LC_TARGET_LINK_SPEED_OVERRIDE_EN; |
WREG32_PCIE_P(PCIE_LC_SPEED_CNTL, speed_cntl); |
WREG32_PCIE_PORT(PCIE_LC_SPEED_CNTL, speed_cntl); |
} |
speed_cntl = RREG32_PCIE_P(PCIE_LC_SPEED_CNTL); |
speed_cntl = RREG32_PCIE_PORT(PCIE_LC_SPEED_CNTL); |
speed_cntl |= LC_GEN2_EN_STRAP; |
WREG32_PCIE_P(PCIE_LC_SPEED_CNTL, speed_cntl); |
WREG32_PCIE_PORT(PCIE_LC_SPEED_CNTL, speed_cntl); |
} else { |
link_width_cntl = RREG32_PCIE_P(PCIE_LC_LINK_WIDTH_CNTL); |
link_width_cntl = RREG32_PCIE_PORT(PCIE_LC_LINK_WIDTH_CNTL); |
/* XXX: only disable it if gen1 bridge vendor == 0x111d or 0x1106 */ |
if (1) |
link_width_cntl |= LC_UPCONFIGURE_DIS; |
else |
link_width_cntl &= ~LC_UPCONFIGURE_DIS; |
WREG32_PCIE_P(PCIE_LC_LINK_WIDTH_CNTL, link_width_cntl); |
WREG32_PCIE_PORT(PCIE_LC_LINK_WIDTH_CNTL, link_width_cntl); |
} |
} |
/** |
* r600_get_gpu_clock - return GPU clock counter snapshot |
* r600_get_gpu_clock_counter - return GPU clock counter snapshot |
* |
* @rdev: radeon_device pointer |
* |
3787,7 → 4292,7 |
* Fetches a GPU clock counter snapshot (R6xx-cayman). |
* Returns the 64 bit clock counter snapshot. |
*/ |
uint64_t r600_get_gpu_clock(struct radeon_device *rdev) |
uint64_t r600_get_gpu_clock_counter(struct radeon_device *rdev) |
{ |
uint64_t clock; |
/drivers/video/drm/radeon/r600_audio.c |
---|
57,10 → 57,7 |
*/ |
static int r600_audio_chipset_supported(struct radeon_device *rdev) |
{ |
return (rdev->family >= CHIP_R600 && !ASIC_IS_DCE6(rdev)) |
|| rdev->family == CHIP_RS600 |
|| rdev->family == CHIP_RS690 |
|| rdev->family == CHIP_RS740; |
return ASIC_IS_DCE2(rdev) && !ASIC_IS_DCE6(rdev); |
} |
struct r600_audio r600_audio_status(struct radeon_device *rdev) |
184,65 → 181,6 |
} |
/* |
* atach the audio codec to the clock source of the encoder |
*/ |
void r600_audio_set_clock(struct drm_encoder *encoder, int clock) |
{ |
struct drm_device *dev = encoder->dev; |
struct radeon_device *rdev = dev->dev_private; |
struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder); |
struct radeon_encoder_atom_dig *dig = radeon_encoder->enc_priv; |
struct radeon_crtc *radeon_crtc = to_radeon_crtc(encoder->crtc); |
int base_rate = 48000; |
switch (radeon_encoder->encoder_id) { |
case ENCODER_OBJECT_ID_INTERNAL_KLDSCP_TMDS1: |
case ENCODER_OBJECT_ID_INTERNAL_LVTM1: |
WREG32_P(R600_AUDIO_TIMING, 0, ~0x301); |
break; |
case ENCODER_OBJECT_ID_INTERNAL_UNIPHY: |
case ENCODER_OBJECT_ID_INTERNAL_UNIPHY1: |
case ENCODER_OBJECT_ID_INTERNAL_UNIPHY2: |
case ENCODER_OBJECT_ID_INTERNAL_KLDSCP_LVTMA: |
WREG32_P(R600_AUDIO_TIMING, 0x100, ~0x301); |
break; |
default: |
dev_err(rdev->dev, "Unsupported encoder type 0x%02X\n", |
radeon_encoder->encoder_id); |
return; |
} |
if (ASIC_IS_DCE4(rdev)) { |
/* TODO: other PLLs? */ |
WREG32(EVERGREEN_AUDIO_PLL1_MUL, base_rate * 10); |
WREG32(EVERGREEN_AUDIO_PLL1_DIV, clock * 10); |
WREG32(EVERGREEN_AUDIO_PLL1_UNK, 0x00000071); |
/* Select DTO source */ |
WREG32(0x5ac, radeon_crtc->crtc_id); |
} else { |
switch (dig->dig_encoder) { |
case 0: |
WREG32(R600_AUDIO_PLL1_MUL, base_rate * 50); |
WREG32(R600_AUDIO_PLL1_DIV, clock * 100); |
WREG32(R600_AUDIO_CLK_SRCSEL, 0); |
break; |
case 1: |
WREG32(R600_AUDIO_PLL2_MUL, base_rate * 50); |
WREG32(R600_AUDIO_PLL2_DIV, clock * 100); |
WREG32(R600_AUDIO_CLK_SRCSEL, 1); |
break; |
default: |
dev_err(rdev->dev, |
"Unsupported DIG on encoder 0x%02X\n", |
radeon_encoder->encoder_id); |
return; |
} |
} |
} |
/* |
* release the audio timer |
* TODO: How to do this correctly on SMP systems? |
*/ |
/drivers/video/drm/radeon/r600_hdmi.c |
---|
23,6 → 23,7 |
* |
* Authors: Christian König |
*/ |
#include <linux/hdmi.h> |
#include <drm/drmP.h> |
#include <drm/radeon_drm.h> |
#include "radeon.h" |
121,43 → 122,10 |
} |
/* |
* calculate the crc for a given info frame |
*/ |
static void r600_hdmi_infoframe_checksum(uint8_t packetType, |
uint8_t versionNumber, |
uint8_t length, |
uint8_t *frame) |
{ |
int i; |
frame[0] = packetType + versionNumber + length; |
for (i = 1; i <= length; i++) |
frame[0] += frame[i]; |
frame[0] = 0x100 - frame[0]; |
} |
/* |
* build a HDMI Video Info Frame |
*/ |
static void r600_hdmi_videoinfoframe( |
struct drm_encoder *encoder, |
enum r600_hdmi_color_format color_format, |
int active_information_present, |
uint8_t active_format_aspect_ratio, |
uint8_t scan_information, |
uint8_t colorimetry, |
uint8_t ex_colorimetry, |
uint8_t quantization, |
int ITC, |
uint8_t picture_aspect_ratio, |
uint8_t video_format_identification, |
uint8_t pixel_repetition, |
uint8_t non_uniform_picture_scaling, |
uint8_t bar_info_data_valid, |
uint16_t top_bar, |
uint16_t bottom_bar, |
uint16_t left_bar, |
uint16_t right_bar |
) |
static void r600_hdmi_update_avi_infoframe(struct drm_encoder *encoder, |
void *buffer, size_t size) |
{ |
struct drm_device *dev = encoder->dev; |
struct radeon_device *rdev = dev->dev_private; |
164,36 → 132,8 |
struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder); |
struct radeon_encoder_atom_dig *dig = radeon_encoder->enc_priv; |
uint32_t offset = dig->afmt->offset; |
uint8_t *frame = buffer + 3; |
uint8_t frame[14]; |
frame[0x0] = 0; |
frame[0x1] = |
(scan_information & 0x3) | |
((bar_info_data_valid & 0x3) << 2) | |
((active_information_present & 0x1) << 4) | |
((color_format & 0x3) << 5); |
frame[0x2] = |
(active_format_aspect_ratio & 0xF) | |
((picture_aspect_ratio & 0x3) << 4) | |
((colorimetry & 0x3) << 6); |
frame[0x3] = |
(non_uniform_picture_scaling & 0x3) | |
((quantization & 0x3) << 2) | |
((ex_colorimetry & 0x7) << 4) | |
((ITC & 0x1) << 7); |
frame[0x4] = (video_format_identification & 0x7F); |
frame[0x5] = (pixel_repetition & 0xF); |
frame[0x6] = (top_bar & 0xFF); |
frame[0x7] = (top_bar >> 8); |
frame[0x8] = (bottom_bar & 0xFF); |
frame[0x9] = (bottom_bar >> 8); |
frame[0xA] = (left_bar & 0xFF); |
frame[0xB] = (left_bar >> 8); |
frame[0xC] = (right_bar & 0xFF); |
frame[0xD] = (right_bar >> 8); |
r600_hdmi_infoframe_checksum(0x82, 0x02, 0x0D, frame); |
/* Our header values (type, version, length) should be alright, Intel |
* is using the same. Checksum function also seems to be OK, it works |
* fine for audio infoframe. However calculated value is always lower |
215,17 → 155,8 |
/* |
* build a Audio Info Frame |
*/ |
static void r600_hdmi_audioinfoframe( |
struct drm_encoder *encoder, |
uint8_t channel_count, |
uint8_t coding_type, |
uint8_t sample_size, |
uint8_t sample_frequency, |
uint8_t format, |
uint8_t channel_allocation, |
uint8_t level_shift, |
int downmix_inhibit |
) |
static void r600_hdmi_update_audio_infoframe(struct drm_encoder *encoder, |
const void *buffer, size_t size) |
{ |
struct drm_device *dev = encoder->dev; |
struct radeon_device *rdev = dev->dev_private; |
232,23 → 163,8 |
struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder); |
struct radeon_encoder_atom_dig *dig = radeon_encoder->enc_priv; |
uint32_t offset = dig->afmt->offset; |
const u8 *frame = buffer + 3; |
uint8_t frame[11]; |
frame[0x0] = 0; |
frame[0x1] = (channel_count & 0x7) | ((coding_type & 0xF) << 4); |
frame[0x2] = (sample_size & 0x3) | ((sample_frequency & 0x7) << 2); |
frame[0x3] = format; |
frame[0x4] = channel_allocation; |
frame[0x5] = ((level_shift & 0xF) << 3) | ((downmix_inhibit & 0x1) << 7); |
frame[0x6] = 0; |
frame[0x7] = 0; |
frame[0x8] = 0; |
frame[0x9] = 0; |
frame[0xA] = 0; |
r600_hdmi_infoframe_checksum(0x84, 0x01, 0x0A, frame); |
WREG32(HDMI0_AUDIO_INFO0 + offset, |
frame[0x0] | (frame[0x1] << 8) | (frame[0x2] << 16) | (frame[0x3] << 24)); |
WREG32(HDMI0_AUDIO_INFO1 + offset, |
310,7 → 226,39 |
value, ~HDMI0_AUDIO_TEST_EN); |
} |
void r600_audio_set_dto(struct drm_encoder *encoder, u32 clock) |
{ |
struct drm_device *dev = encoder->dev; |
struct radeon_device *rdev = dev->dev_private; |
struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder); |
struct radeon_encoder_atom_dig *dig = radeon_encoder->enc_priv; |
u32 base_rate = 24000; |
if (!dig || !dig->afmt) |
return; |
/* there are two DTOs selected by DCCG_AUDIO_DTO_SELECT. |
* doesn't matter which one you use. Just use the first one. |
*/ |
/* XXX two dtos; generally use dto0 for hdmi */ |
/* Express [24MHz / target pixel clock] as an exact rational |
* number (coefficient of two integer numbers. DCCG_AUDIO_DTOx_PHASE |
* is the numerator, DCCG_AUDIO_DTOx_MODULE is the denominator |
*/ |
if (ASIC_IS_DCE3(rdev)) { |
/* according to the reg specs, this should DCE3.2 only, but in |
* practice it seems to cover DCE3.0 as well. |
*/ |
WREG32(DCCG_AUDIO_DTO0_PHASE, base_rate * 100); |
WREG32(DCCG_AUDIO_DTO0_MODULE, clock * 100); |
WREG32(DCCG_AUDIO_DTO_SELECT, 0); /* select DTO0 */ |
} else { |
/* according to the reg specs, this should be DCE2.0 and DCE3.0 */ |
WREG32(AUDIO_DTO, AUDIO_DTO_PHASE(base_rate / 10) | |
AUDIO_DTO_MODULE(clock / 10)); |
} |
} |
/* |
* update the info frames with the data from the current display mode |
*/ |
320,7 → 268,10 |
struct radeon_device *rdev = dev->dev_private; |
struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder); |
struct radeon_encoder_atom_dig *dig = radeon_encoder->enc_priv; |
u8 buffer[HDMI_INFOFRAME_HEADER_SIZE + HDMI_AVI_INFOFRAME_SIZE]; |
struct hdmi_avi_infoframe frame; |
uint32_t offset; |
ssize_t err; |
/* Silent, r600_hdmi_enable will raise WARN for us */ |
if (!dig->afmt->enabled) |
371,9 → 322,19 |
WREG32(HDMI0_GC + offset, 0); /* unset HDMI0_GC_AVMUTE */ |
r600_hdmi_videoinfoframe(encoder, RGB, 0, 0, 0, 0, |
0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0); |
err = drm_hdmi_avi_infoframe_from_display_mode(&frame, mode); |
if (err < 0) { |
DRM_ERROR("failed to setup AVI infoframe: %zd\n", err); |
return; |
} |
err = hdmi_avi_infoframe_pack(&frame, buffer, sizeof(buffer)); |
if (err < 0) { |
DRM_ERROR("failed to pack AVI infoframe: %zd\n", err); |
return; |
} |
r600_hdmi_update_avi_infoframe(encoder, buffer, sizeof(buffer)); |
r600_hdmi_update_ACR(encoder, mode->clock); |
/* it's unknown what these bits do excatly, but it's indeed quite useful for debugging */ |
396,8 → 357,11 |
struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder); |
struct radeon_encoder_atom_dig *dig = radeon_encoder->enc_priv; |
struct r600_audio audio = r600_audio_status(rdev); |
uint8_t buffer[HDMI_INFOFRAME_HEADER_SIZE + HDMI_AUDIO_INFOFRAME_SIZE]; |
struct hdmi_audio_infoframe frame; |
uint32_t offset; |
uint32_t iec; |
ssize_t err; |
if (!dig->afmt || !dig->afmt->enabled) |
return; |
463,9 → 427,21 |
iec |= 0x5 << 16; |
WREG32_P(HDMI0_60958_1 + offset, iec, ~0x5000f); |
r600_hdmi_audioinfoframe(encoder, audio.channels - 1, 0, 0, 0, 0, 0, 0, |
0); |
err = hdmi_audio_infoframe_init(&frame); |
if (err < 0) { |
DRM_ERROR("failed to setup audio infoframe\n"); |
return; |
} |
frame.channels = audio.channels; |
err = hdmi_audio_infoframe_pack(&frame, buffer, sizeof(buffer)); |
if (err < 0) { |
DRM_ERROR("failed to pack audio infoframe\n"); |
return; |
} |
r600_hdmi_update_audio_infoframe(encoder, buffer, sizeof(buffer)); |
r600_hdmi_audio_workaround(encoder); |
} |
#endif |
473,42 → 449,51 |
/* |
* enable the HDMI engine |
*/ |
void r600_hdmi_enable(struct drm_encoder *encoder) |
void r600_hdmi_enable(struct drm_encoder *encoder, bool enable) |
{ |
struct drm_device *dev = encoder->dev; |
struct radeon_device *rdev = dev->dev_private; |
struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder); |
struct radeon_encoder_atom_dig *dig = radeon_encoder->enc_priv; |
uint32_t offset; |
u32 hdmi; |
u32 hdmi = HDMI0_ERROR_ACK; |
if (ASIC_IS_DCE6(rdev)) |
return; |
/* Silent, r600_hdmi_enable will raise WARN for us */ |
if (dig->afmt->enabled) |
if (enable && dig->afmt->enabled) |
return; |
offset = dig->afmt->offset; |
if (!enable && !dig->afmt->enabled) |
return; |
/* Older chipsets require setting HDMI and routing manually */ |
if (rdev->family >= CHIP_R600 && !ASIC_IS_DCE3(rdev)) { |
hdmi = HDMI0_ERROR_ACK | HDMI0_ENABLE; |
if (!ASIC_IS_DCE3(rdev)) { |
if (enable) |
hdmi |= HDMI0_ENABLE; |
switch (radeon_encoder->encoder_id) { |
case ENCODER_OBJECT_ID_INTERNAL_KLDSCP_TMDS1: |
WREG32_P(AVIVO_TMDSA_CNTL, AVIVO_TMDSA_CNTL_HDMI_EN, |
~AVIVO_TMDSA_CNTL_HDMI_EN); |
if (enable) { |
WREG32_OR(AVIVO_TMDSA_CNTL, AVIVO_TMDSA_CNTL_HDMI_EN); |
hdmi |= HDMI0_STREAM(HDMI0_STREAM_TMDSA); |
} else { |
WREG32_AND(AVIVO_TMDSA_CNTL, ~AVIVO_TMDSA_CNTL_HDMI_EN); |
} |
break; |
case ENCODER_OBJECT_ID_INTERNAL_LVTM1: |
WREG32_P(AVIVO_LVTMA_CNTL, AVIVO_LVTMA_CNTL_HDMI_EN, |
~AVIVO_LVTMA_CNTL_HDMI_EN); |
if (enable) { |
WREG32_OR(AVIVO_LVTMA_CNTL, AVIVO_LVTMA_CNTL_HDMI_EN); |
hdmi |= HDMI0_STREAM(HDMI0_STREAM_LVTMA); |
} else { |
WREG32_AND(AVIVO_LVTMA_CNTL, ~AVIVO_LVTMA_CNTL_HDMI_EN); |
} |
break; |
case ENCODER_OBJECT_ID_INTERNAL_DDI: |
WREG32_P(DDIA_CNTL, DDIA_HDMI_EN, ~DDIA_HDMI_EN); |
if (enable) { |
WREG32_OR(DDIA_CNTL, DDIA_HDMI_EN); |
hdmi |= HDMI0_STREAM(HDMI0_STREAM_DDIA); |
} else { |
WREG32_AND(DDIA_CNTL, ~DDIA_HDMI_EN); |
} |
break; |
case ENCODER_OBJECT_ID_INTERNAL_KLDSCP_DVO1: |
if (enable) |
hdmi |= HDMI0_STREAM(HDMI0_STREAM_DVOA); |
break; |
default: |
516,72 → 501,21 |
radeon_encoder->encoder_id); |
break; |
} |
WREG32(HDMI0_CONTROL + offset, hdmi); |
WREG32(HDMI0_CONTROL + dig->afmt->offset, hdmi); |
} |
if (rdev->irq.installed) { |
/* if irq is available use it */ |
/* XXX: shouldn't need this on any asics. Double check DCE2/3 */ |
// if (enable) |
// radeon_irq_kms_enable_afmt(rdev, dig->afmt->id); |
// else |
// radeon_irq_kms_disable_afmt(rdev, dig->afmt->id); |
} |
dig->afmt->enabled = true; |
dig->afmt->enabled = enable; |
DRM_DEBUG("Enabling HDMI interface @ 0x%04X for encoder 0x%x\n", |
offset, radeon_encoder->encoder_id); |
DRM_DEBUG("%sabling HDMI interface @ 0x%04X for encoder 0x%x\n", |
enable ? "En" : "Dis", dig->afmt->offset, radeon_encoder->encoder_id); |
} |
/* |
* disable the HDMI engine |
*/ |
void r600_hdmi_disable(struct drm_encoder *encoder) |
{ |
struct drm_device *dev = encoder->dev; |
struct radeon_device *rdev = dev->dev_private; |
struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder); |
struct radeon_encoder_atom_dig *dig = radeon_encoder->enc_priv; |
uint32_t offset; |
if (ASIC_IS_DCE6(rdev)) |
return; |
/* Called for ATOM_ENCODER_MODE_HDMI only */ |
if (!dig || !dig->afmt) { |
WARN_ON(1); |
return; |
} |
if (!dig->afmt->enabled) |
return; |
offset = dig->afmt->offset; |
DRM_DEBUG("Disabling HDMI interface @ 0x%04X for encoder 0x%x\n", |
offset, radeon_encoder->encoder_id); |
/* disable irq */ |
// radeon_irq_kms_disable_afmt(rdev, dig->afmt->id); |
/* Older chipsets not handled by AtomBIOS */ |
if (rdev->family >= CHIP_R600 && !ASIC_IS_DCE3(rdev)) { |
switch (radeon_encoder->encoder_id) { |
case ENCODER_OBJECT_ID_INTERNAL_KLDSCP_TMDS1: |
WREG32_P(AVIVO_TMDSA_CNTL, 0, |
~AVIVO_TMDSA_CNTL_HDMI_EN); |
break; |
case ENCODER_OBJECT_ID_INTERNAL_LVTM1: |
WREG32_P(AVIVO_LVTMA_CNTL, 0, |
~AVIVO_LVTMA_CNTL_HDMI_EN); |
break; |
case ENCODER_OBJECT_ID_INTERNAL_DDI: |
WREG32_P(DDIA_CNTL, 0, ~DDIA_HDMI_EN); |
break; |
case ENCODER_OBJECT_ID_INTERNAL_KLDSCP_DVO1: |
break; |
default: |
dev_err(rdev->dev, "Invalid encoder for HDMI: 0x%X\n", |
radeon_encoder->encoder_id); |
break; |
} |
WREG32(HDMI0_CONTROL + offset, HDMI0_ERROR_ACK); |
} |
dig->afmt->enabled = false; |
} |
/drivers/video/drm/radeon/r600d.h |
---|
182,6 → 182,8 |
#define CP_COHER_BASE 0x85F8 |
#define CP_DEBUG 0xC1FC |
#define R_0086D8_CP_ME_CNTL 0x86D8 |
#define S_0086D8_CP_PFP_HALT(x) (((x) & 1)<<26) |
#define C_0086D8_CP_PFP_HALT(x) ((x) & 0xFBFFFFFF) |
#define S_0086D8_CP_ME_HALT(x) (((x) & 1)<<28) |
#define C_0086D8_CP_ME_HALT(x) ((x) & 0xEFFFFFFF) |
#define CP_ME_RAM_DATA 0xC160 |
689,6 → 691,7 |
#define SRBM_SOFT_RESET 0xe60 |
# define SOFT_RESET_DMA (1 << 12) |
# define SOFT_RESET_RLC (1 << 13) |
# define SOFT_RESET_UVD (1 << 18) |
# define RV770_SOFT_RESET_DMA (1 << 20) |
#define CP_INT_CNTL 0xc124 |
907,7 → 910,12 |
# define TARGET_LINK_SPEED_MASK (0xf << 0) |
# define SELECTABLE_DEEMPHASIS (1 << 6) |
/* Audio clocks */ |
/* Audio clocks DCE 2.0/3.0 */ |
#define AUDIO_DTO 0x7340 |
# define AUDIO_DTO_PHASE(x) (((x) & 0xffff) << 0) |
# define AUDIO_DTO_MODULE(x) (((x) & 0xffff) << 16) |
/* Audio clocks DCE 3.2 */ |
#define DCCG_AUDIO_DTO0_PHASE 0x0514 |
#define DCCG_AUDIO_DTO0_MODULE 0x0518 |
#define DCCG_AUDIO_DTO0_LOAD 0x051c |
1141,21 → 1149,76 |
# define AFMT_AZ_AUDIO_ENABLE_CHG_ACK (1 << 30) |
/* |
* UVD |
*/ |
#define UVD_SEMA_ADDR_LOW 0xef00 |
#define UVD_SEMA_ADDR_HIGH 0xef04 |
#define UVD_SEMA_CMD 0xef08 |
#define UVD_GPCOM_VCPU_CMD 0xef0c |
#define UVD_GPCOM_VCPU_DATA0 0xef10 |
#define UVD_GPCOM_VCPU_DATA1 0xef14 |
#define UVD_ENGINE_CNTL 0xef18 |
#define UVD_SEMA_CNTL 0xf400 |
#define UVD_RB_ARB_CTRL 0xf480 |
#define UVD_LMI_EXT40_ADDR 0xf498 |
#define UVD_CGC_GATE 0xf4a8 |
#define UVD_LMI_CTRL2 0xf4f4 |
#define UVD_MASTINT_EN 0xf500 |
#define UVD_LMI_ADDR_EXT 0xf594 |
#define UVD_LMI_CTRL 0xf598 |
#define UVD_LMI_SWAP_CNTL 0xf5b4 |
#define UVD_MP_SWAP_CNTL 0xf5bC |
#define UVD_MPC_CNTL 0xf5dC |
#define UVD_MPC_SET_MUXA0 0xf5e4 |
#define UVD_MPC_SET_MUXA1 0xf5e8 |
#define UVD_MPC_SET_MUXB0 0xf5eC |
#define UVD_MPC_SET_MUXB1 0xf5f0 |
#define UVD_MPC_SET_MUX 0xf5f4 |
#define UVD_MPC_SET_ALU 0xf5f8 |
#define UVD_VCPU_CNTL 0xf660 |
#define UVD_SOFT_RESET 0xf680 |
#define RBC_SOFT_RESET (1<<0) |
#define LBSI_SOFT_RESET (1<<1) |
#define LMI_SOFT_RESET (1<<2) |
#define VCPU_SOFT_RESET (1<<3) |
#define CSM_SOFT_RESET (1<<5) |
#define CXW_SOFT_RESET (1<<6) |
#define TAP_SOFT_RESET (1<<7) |
#define LMI_UMC_SOFT_RESET (1<<13) |
#define UVD_RBC_IB_BASE 0xf684 |
#define UVD_RBC_IB_SIZE 0xf688 |
#define UVD_RBC_RB_BASE 0xf68c |
#define UVD_RBC_RB_RPTR 0xf690 |
#define UVD_RBC_RB_WPTR 0xf694 |
#define UVD_RBC_RB_WPTR_CNTL 0xf698 |
#define UVD_STATUS 0xf6bc |
#define UVD_SEMA_TIMEOUT_STATUS 0xf6c0 |
#define UVD_SEMA_WAIT_INCOMPLETE_TIMEOUT_CNTL 0xf6c4 |
#define UVD_SEMA_WAIT_FAULT_TIMEOUT_CNTL 0xf6c8 |
#define UVD_SEMA_SIGNAL_INCOMPLETE_TIMEOUT_CNTL 0xf6cc |
#define UVD_RBC_RB_CNTL 0xf6a4 |
#define UVD_RBC_RB_RPTR_ADDR 0xf6a8 |
#define UVD_CONTEXT_ID 0xf6f4 |
# define UPLL_CTLREQ_MASK 0x00000008 |
# define UPLL_CTLACK_MASK 0x40000000 |
# define UPLL_CTLACK2_MASK 0x80000000 |
/* |
* PM4 |
*/ |
#define PACKET_TYPE0 0 |
#define PACKET_TYPE1 1 |
#define PACKET_TYPE2 2 |
#define PACKET_TYPE3 3 |
#define CP_PACKET_GET_TYPE(h) (((h) >> 30) & 3) |
#define CP_PACKET_GET_COUNT(h) (((h) >> 16) & 0x3FFF) |
#define CP_PACKET0_GET_REG(h) (((h) & 0xFFFF) << 2) |
#define CP_PACKET3_GET_OPCODE(h) (((h) >> 8) & 0xFF) |
#define PACKET0(reg, n) ((PACKET_TYPE0 << 30) | \ |
#define PACKET0(reg, n) ((RADEON_PACKET_TYPE0 << 30) | \ |
(((reg) >> 2) & 0xFFFF) | \ |
((n) & 0x3FFF) << 16) |
#define PACKET3(op, n) ((PACKET_TYPE3 << 30) | \ |
#define PACKET3(op, n) ((RADEON_PACKET_TYPE3 << 30) | \ |
(((op) & 0xFF) << 8) | \ |
((n) & 0x3FFF) << 16) |
1279,6 → 1342,14 |
#define PACKET3_STRMOUT_BASE_UPDATE 0x72 /* r7xx */ |
#define PACKET3_SURFACE_BASE_UPDATE 0x73 |
#define R_000011_K8_FB_LOCATION 0x11 |
#define R_000012_MC_MISC_UMA_CNTL 0x12 |
#define G_000012_K8_ADDR_EXT(x) (((x) >> 0) & 0xFF) |
#define R_0028F8_MC_INDEX 0x28F8 |
#define S_0028F8_MC_IND_ADDR(x) (((x) & 0x1FF) << 0) |
#define C_0028F8_MC_IND_ADDR 0xFFFFFE00 |
#define S_0028F8_MC_IND_WR_EN(x) (((x) & 0x1) << 9) |
#define R_0028FC_MC_DATA 0x28FC |
#define R_008020_GRBM_SOFT_RESET 0x8020 |
#define S_008020_SOFT_RESET_CP(x) (((x) & 1) << 0) |
1328,6 → 1399,7 |
#define G_008010_VC_BUSY(x) (((x) >> 11) & 1) |
#define G_008010_DB03_CLEAN(x) (((x) >> 12) & 1) |
#define G_008010_CB03_CLEAN(x) (((x) >> 13) & 1) |
#define G_008010_TA_BUSY(x) (((x) >> 14) & 1) |
#define G_008010_VGT_BUSY_NO_DMA(x) (((x) >> 16) & 1) |
#define G_008010_VGT_BUSY(x) (((x) >> 17) & 1) |
#define G_008010_TA03_BUSY(x) (((x) >> 18) & 1) |
1395,6 → 1467,7 |
#define G_000E50_MCDW_BUSY(x) (((x) >> 13) & 1) |
#define G_000E50_SEM_BUSY(x) (((x) >> 14) & 1) |
#define G_000E50_RLC_BUSY(x) (((x) >> 15) & 1) |
#define G_000E50_IH_BUSY(x) (((x) >> 17) & 1) |
#define G_000E50_BIF_BUSY(x) (((x) >> 29) & 1) |
#define R_000E60_SRBM_SOFT_RESET 0x0E60 |
#define S_000E60_SOFT_RESET_BIF(x) (((x) & 1) << 1) |
/drivers/video/drm/radeon/radeon.h |
---|
102,9 → 102,9 |
extern int radeon_pcie_gen2; |
extern int radeon_msi; |
extern int radeon_lockup_timeout; |
extern int radeon_fastfb; |
typedef struct pm_message { |
int event; |
} pm_message_t; |
124,10 → 124,10 |
return in32((u32)addr); |
} |
static inline void iowrite32(uint32_t b, volatile void __iomem *addr) |
{ |
out32((u32)addr, b); |
} |
//static inline void iowrite32(uint32_t b, volatile void __iomem *addr) |
//{ |
// out32((u32)addr, b); |
//} |
/* |
143,7 → 143,7 |
#define RADEON_BIOS_NUM_SCRATCH 8 |
/* max number of rings */ |
#define RADEON_NUM_RINGS 5 |
#define RADEON_NUM_RINGS 6 |
/* fence seq are set to this number when signaled */ |
#define RADEON_FENCE_SIGNALED_SEQ 0LL |
161,6 → 161,9 |
/* cayman add a second async dma ring */ |
#define CAYMAN_RING_TYPE_DMA1_INDEX 4 |
/* R600+ */ |
#define R600_RING_TYPE_UVD_INDEX 5 |
/* hardcode those limit for now */ |
#define RADEON_VA_IB_OFFSET (1 << 20) |
#define RADEON_VA_RESERVED_SIZE (8 << 20) |
170,6 → 173,15 |
#define RADEON_RESET_GFX (1 << 0) |
#define RADEON_RESET_COMPUTE (1 << 1) |
#define RADEON_RESET_DMA (1 << 2) |
#define RADEON_RESET_CP (1 << 3) |
#define RADEON_RESET_GRBM (1 << 4) |
#define RADEON_RESET_DMA1 (1 << 5) |
#define RADEON_RESET_RLC (1 << 6) |
#define RADEON_RESET_SEM (1 << 7) |
#define RADEON_RESET_IH (1 << 8) |
#define RADEON_RESET_VMC (1 << 9) |
#define RADEON_RESET_MC (1 << 10) |
#define RADEON_RESET_DISPLAY (1 << 11) |
/* |
* Errata workarounds. |
227,6 → 239,11 |
void radeon_pm_resume(struct radeon_device *rdev); |
void radeon_combios_get_power_modes(struct radeon_device *rdev); |
void radeon_atombios_get_power_modes(struct radeon_device *rdev); |
int radeon_atom_get_clock_dividers(struct radeon_device *rdev, |
u8 clock_type, |
u32 clock, |
bool strobe_mode, |
struct atom_clock_dividers *dividers); |
void radeon_atom_set_voltage(struct radeon_device *rdev, u16 voltage_level, u8 voltage_type); |
void rs690_pm_info(struct radeon_device *rdev); |
extern int rv6xx_get_temp(struct radeon_device *rdev); |
329,7 → 346,7 |
*/ |
struct radeon_mman { |
struct ttm_bo_global_ref bo_global_ref; |
// struct drm_global_reference mem_global_ref; |
struct drm_global_reference mem_global_ref; |
struct ttm_bo_device bdev; |
bool mem_global_referenced; |
bool initialized; |
358,7 → 375,7 |
struct list_head list; |
/* Protected by tbo.reserved */ |
u32 placements[3]; |
u32 busy_placements[3]; |
u32 domain; |
struct ttm_placement placement; |
struct ttm_buffer_object tbo; |
struct ttm_bo_kmap_obj kmap; |
377,8 → 394,7 |
struct radeon_device *rdev; |
struct drm_gem_object gem_base; |
u32 domain; |
int vmapping_count; |
struct ttm_bo_kmap_obj dma_buf_vmap; |
}; |
#define gem_to_radeon_bo(gobj) container_of((gobj), struct radeon_bo, gem_base) |
390,6 → 406,8 |
u32 tiling_flags; |
}; |
int radeon_gem_debugfs_init(struct radeon_device *rdev); |
/* sub-allocation manager, it has to be protected by another lock. |
* By conception this is an helper for other part of the driver |
* like the indirect buffer or semaphore, which both have their |
545,6 → 563,7 |
bool vram_is_ddr; |
bool igp_sideport_enabled; |
u64 gtt_base_align; |
u64 mc_mask; |
}; |
bool radeon_combios_sideport_present(struct radeon_device *rdev); |
678,6 → 697,8 |
u32 ptr_reg_mask; |
u32 nop; |
u32 idx; |
u64 last_semaphore_signal_addr; |
u64 last_semaphore_wait_addr; |
}; |
/* |
794,6 → 815,7 |
struct radeon_ib *ib, struct radeon_vm *vm, |
unsigned size); |
void radeon_ib_free(struct radeon_device *rdev, struct radeon_ib *ib); |
void radeon_ib_sync_to(struct radeon_ib *ib, struct radeon_fence *fence); |
int radeon_ib_schedule(struct radeon_device *rdev, struct radeon_ib *ib, |
struct radeon_ib *const_ib); |
int radeon_ib_pool_init(struct radeon_device *rdev); |
932,6 → 954,7 |
#define R600_WB_DMA_RPTR_OFFSET 1792 |
#define R600_WB_IH_WPTR_OFFSET 2048 |
#define CAYMAN_WB_DMA1_RPTR_OFFSET 2304 |
#define R600_WB_UVD_RPTR_OFFSET 2560 |
#define R600_WB_EVENT_OFFSET 3072 |
/** |
1132,7 → 1155,47 |
int radeon_pm_get_type_index(struct radeon_device *rdev, |
enum radeon_pm_state_type ps_type, |
int instance); |
/* |
* UVD |
*/ |
#define RADEON_MAX_UVD_HANDLES 10 |
#define RADEON_UVD_STACK_SIZE (1024*1024) |
#define RADEON_UVD_HEAP_SIZE (1024*1024) |
struct radeon_uvd { |
struct radeon_bo *vcpu_bo; |
void *cpu_addr; |
uint64_t gpu_addr; |
atomic_t handles[RADEON_MAX_UVD_HANDLES]; |
struct drm_file *filp[RADEON_MAX_UVD_HANDLES]; |
struct delayed_work idle_work; |
}; |
int radeon_uvd_init(struct radeon_device *rdev); |
void radeon_uvd_fini(struct radeon_device *rdev); |
int radeon_uvd_suspend(struct radeon_device *rdev); |
int radeon_uvd_resume(struct radeon_device *rdev); |
int radeon_uvd_get_create_msg(struct radeon_device *rdev, int ring, |
uint32_t handle, struct radeon_fence **fence); |
int radeon_uvd_get_destroy_msg(struct radeon_device *rdev, int ring, |
uint32_t handle, struct radeon_fence **fence); |
void radeon_uvd_force_into_uvd_segment(struct radeon_bo *rbo); |
void radeon_uvd_free_handles(struct radeon_device *rdev, |
struct drm_file *filp); |
int radeon_uvd_cs_parse(struct radeon_cs_parser *parser); |
void radeon_uvd_note_usage(struct radeon_device *rdev); |
int radeon_uvd_calc_upll_dividers(struct radeon_device *rdev, |
unsigned vclk, unsigned dclk, |
unsigned vco_min, unsigned vco_max, |
unsigned fb_factor, unsigned fb_mask, |
unsigned pd_min, unsigned pd_max, |
unsigned pd_even, |
unsigned *optimal_fb_div, |
unsigned *optimal_vclk_div, |
unsigned *optimal_dclk_div); |
int radeon_uvd_send_upll_ctlreq(struct radeon_device *rdev, |
unsigned cg_upll_func_cntl); |
struct r600_audio { |
int channels; |
int rate; |
1161,6 → 1224,10 |
bool (*gui_idle)(struct radeon_device *rdev); |
/* wait for mc_idle */ |
int (*mc_wait_for_idle)(struct radeon_device *rdev); |
/* get the reference clock */ |
u32 (*get_xclk)(struct radeon_device *rdev); |
/* get the gpu clock counter */ |
uint64_t (*get_gpu_clock_counter)(struct radeon_device *rdev); |
/* gart */ |
struct { |
void (*tlb_flush)(struct radeon_device *rdev); |
1171,7 → 1238,9 |
void (*fini)(struct radeon_device *rdev); |
u32 pt_ring_index; |
void (*set_page)(struct radeon_device *rdev, uint64_t pe, |
void (*set_page)(struct radeon_device *rdev, |
struct radeon_ib *ib, |
uint64_t pe, |
uint64_t addr, unsigned count, |
uint32_t incr, uint32_t flags); |
} vm; |
1206,6 → 1275,9 |
void (*set_backlight_level)(struct radeon_encoder *radeon_encoder, u8 level); |
/* get backlight level */ |
u8 (*get_backlight_level)(struct radeon_encoder *radeon_encoder); |
/* audio callbacks */ |
void (*hdmi_enable)(struct drm_encoder *encoder, bool enable); |
void (*hdmi_setmode)(struct drm_encoder *encoder, struct drm_display_mode *mode); |
} display; |
/* copy functions for bo handling */ |
struct { |
1258,6 → 1330,7 |
int (*get_pcie_lanes)(struct radeon_device *rdev); |
void (*set_pcie_lanes)(struct radeon_device *rdev, int lanes); |
void (*set_clock_gating)(struct radeon_device *rdev, int enable); |
int (*set_uvd_clocks)(struct radeon_device *rdev, u32 vclk, u32 dclk); |
} pm; |
/* pageflipping */ |
struct { |
1420,6 → 1493,7 |
unsigned multi_gpu_tile_size; |
unsigned tile_config; |
uint32_t tile_mode_array[32]; |
}; |
union radeon_asic_config { |
1505,6 → 1579,7 |
struct radeon_asic *asic; |
struct radeon_gem gem; |
struct radeon_pm pm; |
struct radeon_uvd uvd; |
uint32_t bios_scratch[RADEON_BIOS_NUM_SCRATCH]; |
struct radeon_wb wb; |
struct radeon_dummy_page dummy_page; |
1512,6 → 1587,7 |
bool suspend; |
bool need_dma32; |
bool accel_working; |
bool fastfb_working; /* IGP feature*/ |
struct radeon_surface_reg surface_regs[RADEON_GEM_MAX_SURFACES]; |
const struct firmware *me_fw; /* all family ME firmware */ |
const struct firmware *pfp_fw; /* r6/700 PFP firmware */ |
1518,6 → 1594,7 |
const struct firmware *rlc_fw; /* r6/700 RLC firmware */ |
const struct firmware *mc_fw; /* NI MC firmware */ |
const struct firmware *ce_fw; /* SI CE firmware */ |
const struct firmware *uvd_fw; /* UVD firmware */ |
struct r600_blit r600_blit; |
struct r600_vram_scratch vram_scratch; |
int msi_enabled; /* msi enabled */ |
1528,6 → 1605,7 |
int num_crtc; /* number of crtcs */ |
struct mutex dc_hw_i2c_mutex; /* display controller hw i2c mutex */ |
bool audio_enabled; |
bool has_uvd; |
// struct r600_audio audio_status; /* audio stuff */ |
// struct notifier_block acpi_nb; |
/* only one userspace can use Hyperz features or CMASK at a time */ |
1585,8 → 1663,8 |
#define WREG32_MC(reg, v) rdev->mc_wreg(rdev, (reg), (v)) |
#define RREG32_PCIE(reg) rv370_pcie_rreg(rdev, (reg)) |
#define WREG32_PCIE(reg, v) rv370_pcie_wreg(rdev, (reg), (v)) |
#define RREG32_PCIE_P(reg) rdev->pciep_rreg(rdev, (reg)) |
#define WREG32_PCIE_P(reg, v) rdev->pciep_wreg(rdev, (reg), (v)) |
#define RREG32_PCIE_PORT(reg) rdev->pciep_rreg(rdev, (reg)) |
#define WREG32_PCIE_PORT(reg, v) rdev->pciep_wreg(rdev, (reg), (v)) |
#define WREG32_P(reg, val, mask) \ |
do { \ |
uint32_t tmp_ = RREG32(reg); \ |
1594,6 → 1672,8 |
tmp_ |= ((val) & ~(mask)); \ |
WREG32(reg, tmp_); \ |
} while (0) |
#define WREG32_AND(reg, and) WREG32_P(reg, 0, and) |
#define WREG32_OR(reg, or) WREG32_P(reg, or, ~or) |
#define WREG32_PLL_P(reg, val, mask) \ |
do { \ |
uint32_t tmp_ = RREG32_PLL(reg); \ |
1668,6 → 1748,8 |
#define ASIC_IS_DCE6(rdev) ((rdev->family >= CHIP_ARUBA)) |
#define ASIC_IS_DCE61(rdev) ((rdev->family >= CHIP_ARUBA) && \ |
(rdev->flags & RADEON_IS_IGP)) |
#define ASIC_IS_DCE64(rdev) ((rdev->family == CHIP_OLAND)) |
#define ASIC_IS_NODCE(rdev) ((rdev->family == CHIP_HAINAN)) |
/* |
* BIOS helpers. |
1712,7 → 1794,7 |
#define radeon_gart_set_page(rdev, i, p) (rdev)->asic->gart.set_page((rdev), (i), (p)) |
#define radeon_asic_vm_init(rdev) (rdev)->asic->vm.init((rdev)) |
#define radeon_asic_vm_fini(rdev) (rdev)->asic->vm.fini((rdev)) |
#define radeon_asic_vm_set_page(rdev, pe, addr, count, incr, flags) ((rdev)->asic->vm.set_page((rdev), (pe), (addr), (count), (incr), (flags))) |
#define radeon_asic_vm_set_page(rdev, ib, pe, addr, count, incr, flags) ((rdev)->asic->vm.set_page((rdev), (ib), (pe), (addr), (count), (incr), (flags))) |
#define radeon_ring_start(rdev, r, cp) (rdev)->asic->ring[(r)].ring_start((rdev), (cp)) |
#define radeon_ring_test(rdev, r, cp) (rdev)->asic->ring[(r)].ring_test((rdev), (cp)) |
#define radeon_ib_test(rdev, r, cp) (rdev)->asic->ring[(r)].ib_test((rdev), (cp)) |
1725,6 → 1807,8 |
#define radeon_get_vblank_counter(rdev, crtc) (rdev)->asic->display.get_vblank_counter((rdev), (crtc)) |
#define radeon_set_backlight_level(rdev, e, l) (rdev)->asic->display.set_backlight_level((e), (l)) |
#define radeon_get_backlight_level(rdev, e) (rdev)->asic->display.get_backlight_level((e)) |
#define radeon_hdmi_enable(rdev, e, b) (rdev)->asic->display.hdmi_enable((e), (b)) |
#define radeon_hdmi_setmode(rdev, e, m) (rdev)->asic->display.hdmi_setmode((e), (m)) |
#define radeon_fence_ring_emit(rdev, r, fence) (rdev)->asic->ring[(r)].emit_fence((rdev), (fence)) |
#define radeon_semaphore_ring_emit(rdev, r, cp, semaphore, emit_wait) (rdev)->asic->ring[(r)].emit_semaphore((rdev), (cp), (semaphore), (emit_wait)) |
#define radeon_copy_blit(rdev, s, d, np, f) (rdev)->asic->copy.blit((rdev), (s), (d), (np), (f)) |
1740,6 → 1824,7 |
#define radeon_get_pcie_lanes(rdev) (rdev)->asic->pm.get_pcie_lanes((rdev)) |
#define radeon_set_pcie_lanes(rdev, l) (rdev)->asic->pm.set_pcie_lanes((rdev), (l)) |
#define radeon_set_clock_gating(rdev, e) (rdev)->asic->pm.set_clock_gating((rdev), (e)) |
#define radeon_set_uvd_clocks(rdev, v, d) (rdev)->asic->pm.set_uvd_clocks((rdev), (v), (d)) |
#define radeon_set_surface_reg(rdev, r, f, p, o, s) ((rdev)->asic->surface.set_reg((rdev), (r), (f), (p), (o), (s))) |
#define radeon_clear_surface_reg(rdev, r) ((rdev)->asic->surface.clear_reg((rdev), (r))) |
#define radeon_bandwidth_update(rdev) (rdev)->asic->display.bandwidth_update((rdev)) |
1758,10 → 1843,13 |
#define radeon_post_page_flip(rdev, crtc) (rdev)->asic->pflip.post_page_flip((rdev), (crtc)) |
#define radeon_wait_for_vblank(rdev, crtc) (rdev)->asic->display.wait_for_vblank((rdev), (crtc)) |
#define radeon_mc_wait_for_idle(rdev) (rdev)->asic->mc_wait_for_idle((rdev)) |
#define radeon_get_xclk(rdev) (rdev)->asic->get_xclk((rdev)) |
#define radeon_get_gpu_clock_counter(rdev) (rdev)->asic->get_gpu_clock_counter((rdev)) |
/* Common functions */ |
/* AGP */ |
extern int radeon_gpu_reset(struct radeon_device *rdev); |
extern void r600_set_bios_scratch_engine_hung(struct radeon_device *rdev, bool hung); |
extern void radeon_agp_disable(struct radeon_device *rdev); |
extern int radeon_modeset_init(struct radeon_device *rdev); |
extern void radeon_modeset_fini(struct radeon_device *rdev); |
1784,6 → 1872,9 |
extern int radeon_resume_kms(struct drm_device *dev); |
extern int radeon_suspend_kms(struct drm_device *dev, pm_message_t state); |
extern void radeon_ttm_set_active_vram_size(struct radeon_device *rdev, u64 size); |
extern void radeon_program_register_sequence(struct radeon_device *rdev, |
const u32 *registers, |
const u32 array_size); |
/* |
* vm |
1856,9 → 1947,6 |
extern struct radeon_hdmi_acr r600_hdmi_acr(uint32_t clock); |
extern void r600_hdmi_enable(struct drm_encoder *encoder); |
extern void r600_hdmi_disable(struct drm_encoder *encoder); |
extern void r600_hdmi_setmode(struct drm_encoder *encoder, struct drm_display_mode *mode); |
extern u32 r6xx_remap_render_backend(struct radeon_device *rdev, |
u32 tiling_pipe_num, |
u32 max_rb_num, |
1869,8 → 1957,6 |
* evergreen functions used by radeon_encoder.c |
*/ |
extern void evergreen_hdmi_setmode(struct drm_encoder *encoder, struct drm_display_mode *mode); |
extern int ni_init_microcode(struct radeon_device *rdev); |
extern int ni_mc_load_microcode(struct radeon_device *rdev); |
1896,7 → 1982,8 |
videomode_t *mode, bool strict); |
#ifndef __TTM__ |
#define radeon_ttm_set_active_vram_size(a, b) |
#endif |
#endif |
/drivers/video/drm/radeon/radeon_asic.c |
---|
122,6 → 122,10 |
rdev->mc_rreg = &rs600_mc_rreg; |
rdev->mc_wreg = &rs600_mc_wreg; |
} |
if (rdev->family == CHIP_RS780 || rdev->family == CHIP_RS880) { |
rdev->mc_rreg = &rs780_mc_rreg; |
rdev->mc_wreg = &rs780_mc_wreg; |
} |
if (rdev->family >= CHIP_R600) { |
rdev->pciep_rreg = &r600_pciep_rreg; |
rdev->pciep_wreg = &r600_pciep_wreg; |
934,6 → 938,8 |
// .ioctl_wait_idle = r600_ioctl_wait_idle, |
.gui_idle = &r600_gui_idle, |
.mc_wait_for_idle = &r600_mc_wait_for_idle, |
.get_xclk = &r600_get_xclk, |
.get_gpu_clock_counter = &r600_get_gpu_clock_counter, |
.gart = { |
.tlb_flush = &r600_pcie_gart_tlb_flush, |
.set_page = &rs600_gart_set_page, |
946,7 → 952,7 |
// .cs_parse = &r600_cs_parse, |
.ring_test = &r600_ring_test, |
.ib_test = &r600_ib_test, |
.is_lockup = &r600_gpu_is_lockup, |
.is_lockup = &r600_gfx_is_lockup, |
}, |
[R600_RING_TYPE_DMA_INDEX] = { |
.ib_execute = &r600_dma_ring_ib_execute, |
1018,6 → 1024,8 |
// .ioctl_wait_idle = r600_ioctl_wait_idle, |
.gui_idle = &r600_gui_idle, |
.mc_wait_for_idle = &r600_mc_wait_for_idle, |
.get_xclk = &r600_get_xclk, |
.get_gpu_clock_counter = &r600_get_gpu_clock_counter, |
.gart = { |
.tlb_flush = &r600_pcie_gart_tlb_flush, |
.set_page = &rs600_gart_set_page, |
1030,7 → 1038,7 |
// .cs_parse = &r600_cs_parse, |
.ring_test = &r600_ring_test, |
.ib_test = &r600_ib_test, |
.is_lockup = &r600_gpu_is_lockup, |
.is_lockup = &r600_gfx_is_lockup, |
}, |
[R600_RING_TYPE_DMA_INDEX] = { |
.ib_execute = &r600_dma_ring_ib_execute, |
1102,6 → 1110,8 |
// .ioctl_wait_idle = r600_ioctl_wait_idle, |
.gui_idle = &r600_gui_idle, |
.mc_wait_for_idle = &r600_mc_wait_for_idle, |
.get_xclk = &rv770_get_xclk, |
.get_gpu_clock_counter = &r600_get_gpu_clock_counter, |
.gart = { |
.tlb_flush = &r600_pcie_gart_tlb_flush, |
.set_page = &rs600_gart_set_page, |
1114,7 → 1124,7 |
// .cs_parse = &r600_cs_parse, |
.ring_test = &r600_ring_test, |
.ib_test = &r600_ib_test, |
.is_lockup = &r600_gpu_is_lockup, |
.is_lockup = &r600_gfx_is_lockup, |
}, |
[R600_RING_TYPE_DMA_INDEX] = { |
.ib_execute = &r600_dma_ring_ib_execute, |
1124,6 → 1134,15 |
.ring_test = &r600_dma_ring_test, |
.ib_test = &r600_dma_ib_test, |
.is_lockup = &r600_dma_is_lockup, |
}, |
[R600_RING_TYPE_UVD_INDEX] = { |
// .ib_execute = &r600_uvd_ib_execute, |
// .emit_fence = &r600_uvd_fence_emit, |
// .emit_semaphore = &r600_uvd_semaphore_emit, |
// .cs_parse = &radeon_uvd_cs_parse, |
// .ring_test = &r600_uvd_ring_test, |
// .ib_test = &r600_uvd_ib_test, |
// .is_lockup = &radeon_ring_test_lockup, |
} |
}, |
.irq = { |
1140,9 → 1159,9 |
.copy = { |
.blit = &r600_copy_blit, |
.blit_ring_index = RADEON_RING_TYPE_GFX_INDEX, |
.dma = &r600_copy_dma, |
.dma = &rv770_copy_dma, |
.dma_ring_index = R600_RING_TYPE_DMA_INDEX, |
.copy = &r600_copy_dma, |
.copy = &rv770_copy_dma, |
.copy_ring_index = R600_RING_TYPE_DMA_INDEX, |
}, |
.surface = { |
1168,6 → 1187,7 |
// .get_pcie_lanes = &r600_get_pcie_lanes, |
// .set_pcie_lanes = &r600_set_pcie_lanes, |
// .set_clock_gating = &radeon_atom_set_clock_gating, |
.set_uvd_clocks = &rv770_set_uvd_clocks, |
}, |
.pflip = { |
// .pre_page_flip = &rs600_pre_page_flip, |
1186,6 → 1206,8 |
// .ioctl_wait_idle = r600_ioctl_wait_idle, |
.gui_idle = &r600_gui_idle, |
.mc_wait_for_idle = &evergreen_mc_wait_for_idle, |
.get_xclk = &rv770_get_xclk, |
.get_gpu_clock_counter = &r600_get_gpu_clock_counter, |
.gart = { |
.tlb_flush = &evergreen_pcie_gart_tlb_flush, |
.set_page = &rs600_gart_set_page, |
1198,7 → 1220,7 |
// .cs_parse = &evergreen_cs_parse, |
.ring_test = &r600_ring_test, |
.ib_test = &r600_ib_test, |
.is_lockup = &evergreen_gpu_is_lockup, |
.is_lockup = &evergreen_gfx_is_lockup, |
}, |
[R600_RING_TYPE_DMA_INDEX] = { |
.ib_execute = &evergreen_dma_ring_ib_execute, |
1207,7 → 1229,16 |
// .cs_parse = &evergreen_dma_cs_parse, |
.ring_test = &r600_dma_ring_test, |
.ib_test = &r600_dma_ib_test, |
.is_lockup = &r600_dma_is_lockup, |
.is_lockup = &evergreen_dma_is_lockup, |
}, |
[R600_RING_TYPE_UVD_INDEX] = { |
// .ib_execute = &r600_uvd_ib_execute, |
// .emit_fence = &r600_uvd_fence_emit, |
// .emit_semaphore = &r600_uvd_semaphore_emit, |
// .cs_parse = &radeon_uvd_cs_parse, |
// .ring_test = &r600_uvd_ring_test, |
// .ib_test = &r600_uvd_ib_test, |
// .is_lockup = &radeon_ring_test_lockup, |
} |
}, |
.irq = { |
1252,6 → 1283,7 |
// .get_pcie_lanes = &r600_get_pcie_lanes, |
// .set_pcie_lanes = &r600_set_pcie_lanes, |
// .set_clock_gating = NULL, |
.set_uvd_clocks = &evergreen_set_uvd_clocks, |
}, |
.pflip = { |
// .pre_page_flip = &evergreen_pre_page_flip, |
1270,6 → 1302,8 |
// .ioctl_wait_idle = r600_ioctl_wait_idle, |
.gui_idle = &r600_gui_idle, |
.mc_wait_for_idle = &evergreen_mc_wait_for_idle, |
.get_xclk = &r600_get_xclk, |
.get_gpu_clock_counter = &r600_get_gpu_clock_counter, |
.gart = { |
.tlb_flush = &evergreen_pcie_gart_tlb_flush, |
.set_page = &rs600_gart_set_page, |
1282,7 → 1316,7 |
// .cs_parse = &evergreen_cs_parse, |
.ring_test = &r600_ring_test, |
.ib_test = &r600_ib_test, |
.is_lockup = &evergreen_gpu_is_lockup, |
.is_lockup = &evergreen_gfx_is_lockup, |
}, |
[R600_RING_TYPE_DMA_INDEX] = { |
.ib_execute = &evergreen_dma_ring_ib_execute, |
1291,7 → 1325,16 |
// .cs_parse = &evergreen_dma_cs_parse, |
.ring_test = &r600_dma_ring_test, |
.ib_test = &r600_dma_ib_test, |
.is_lockup = &r600_dma_is_lockup, |
.is_lockup = &evergreen_dma_is_lockup, |
}, |
[R600_RING_TYPE_UVD_INDEX] = { |
// .ib_execute = &r600_uvd_ib_execute, |
// .emit_fence = &r600_uvd_fence_emit, |
// .emit_semaphore = &r600_uvd_semaphore_emit, |
// .cs_parse = &radeon_uvd_cs_parse, |
// .ring_test = &r600_uvd_ring_test, |
// .ib_test = &r600_uvd_ib_test, |
// .is_lockup = &radeon_ring_test_lockup, |
} |
}, |
.irq = { |
1336,6 → 1379,7 |
.get_pcie_lanes = NULL, |
.set_pcie_lanes = NULL, |
.set_clock_gating = NULL, |
.set_uvd_clocks = &sumo_set_uvd_clocks, |
}, |
.pflip = { |
// .pre_page_flip = &evergreen_pre_page_flip, |
1354,6 → 1398,8 |
// .ioctl_wait_idle = r600_ioctl_wait_idle, |
.gui_idle = &r600_gui_idle, |
.mc_wait_for_idle = &evergreen_mc_wait_for_idle, |
.get_xclk = &rv770_get_xclk, |
.get_gpu_clock_counter = &r600_get_gpu_clock_counter, |
.gart = { |
.tlb_flush = &evergreen_pcie_gart_tlb_flush, |
.set_page = &rs600_gart_set_page, |
1366,7 → 1412,7 |
// .cs_parse = &evergreen_cs_parse, |
.ring_test = &r600_ring_test, |
.ib_test = &r600_ib_test, |
.is_lockup = &evergreen_gpu_is_lockup, |
.is_lockup = &evergreen_gfx_is_lockup, |
}, |
[R600_RING_TYPE_DMA_INDEX] = { |
.ib_execute = &evergreen_dma_ring_ib_execute, |
1375,7 → 1421,16 |
// .cs_parse = &evergreen_dma_cs_parse, |
.ring_test = &r600_dma_ring_test, |
.ib_test = &r600_dma_ib_test, |
.is_lockup = &r600_dma_is_lockup, |
.is_lockup = &evergreen_dma_is_lockup, |
}, |
[R600_RING_TYPE_UVD_INDEX] = { |
// .ib_execute = &r600_uvd_ib_execute, |
// .emit_fence = &r600_uvd_fence_emit, |
// .emit_semaphore = &r600_uvd_semaphore_emit, |
// .cs_parse = &radeon_uvd_cs_parse, |
// .ring_test = &r600_uvd_ring_test, |
// .ib_test = &r600_uvd_ib_test, |
// .is_lockup = &radeon_ring_test_lockup, |
} |
}, |
.irq = { |
1420,6 → 1475,7 |
.get_pcie_lanes = NULL, |
.set_pcie_lanes = NULL, |
.set_clock_gating = NULL, |
.set_uvd_clocks = &evergreen_set_uvd_clocks, |
}, |
.pflip = { |
// .pre_page_flip = &evergreen_pre_page_flip, |
1438,6 → 1494,8 |
// .ioctl_wait_idle = r600_ioctl_wait_idle, |
.gui_idle = &r600_gui_idle, |
.mc_wait_for_idle = &evergreen_mc_wait_for_idle, |
.get_xclk = &rv770_get_xclk, |
.get_gpu_clock_counter = &r600_get_gpu_clock_counter, |
.gart = { |
.tlb_flush = &cayman_pcie_gart_tlb_flush, |
.set_page = &rs600_gart_set_page, |
1457,7 → 1515,7 |
// .cs_parse = &evergreen_cs_parse, |
.ring_test = &r600_ring_test, |
.ib_test = &r600_ib_test, |
.is_lockup = &evergreen_gpu_is_lockup, |
.is_lockup = &cayman_gfx_is_lockup, |
.vm_flush = &cayman_vm_flush, |
}, |
[CAYMAN_RING_TYPE_CP1_INDEX] = { |
1468,7 → 1526,7 |
// .cs_parse = &evergreen_cs_parse, |
.ring_test = &r600_ring_test, |
.ib_test = &r600_ib_test, |
.is_lockup = &evergreen_gpu_is_lockup, |
.is_lockup = &cayman_gfx_is_lockup, |
.vm_flush = &cayman_vm_flush, |
}, |
[CAYMAN_RING_TYPE_CP2_INDEX] = { |
1479,7 → 1537,7 |
// .cs_parse = &evergreen_cs_parse, |
.ring_test = &r600_ring_test, |
.ib_test = &r600_ib_test, |
.is_lockup = &evergreen_gpu_is_lockup, |
.is_lockup = &cayman_gfx_is_lockup, |
.vm_flush = &cayman_vm_flush, |
}, |
[R600_RING_TYPE_DMA_INDEX] = { |
1503,6 → 1561,15 |
.ib_test = &r600_dma_ib_test, |
.is_lockup = &cayman_dma_is_lockup, |
.vm_flush = &cayman_dma_vm_flush, |
}, |
[R600_RING_TYPE_UVD_INDEX] = { |
// .ib_execute = &r600_uvd_ib_execute, |
// .emit_fence = &r600_uvd_fence_emit, |
// .emit_semaphore = &cayman_uvd_semaphore_emit, |
// .cs_parse = &radeon_uvd_cs_parse, |
// .ring_test = &r600_uvd_ring_test, |
// .ib_test = &r600_uvd_ib_test, |
// .is_lockup = &radeon_ring_test_lockup, |
} |
}, |
.irq = { |
1547,6 → 1614,7 |
.get_pcie_lanes = NULL, |
.set_pcie_lanes = NULL, |
.set_clock_gating = NULL, |
.set_uvd_clocks = &evergreen_set_uvd_clocks, |
}, |
.pflip = { |
// .pre_page_flip = &evergreen_pre_page_flip, |
1565,6 → 1633,8 |
// .ioctl_wait_idle = r600_ioctl_wait_idle, |
.gui_idle = &r600_gui_idle, |
.mc_wait_for_idle = &evergreen_mc_wait_for_idle, |
.get_xclk = &r600_get_xclk, |
.get_gpu_clock_counter = &r600_get_gpu_clock_counter, |
.gart = { |
.tlb_flush = &cayman_pcie_gart_tlb_flush, |
.set_page = &rs600_gart_set_page, |
1584,7 → 1654,7 |
// .cs_parse = &evergreen_cs_parse, |
.ring_test = &r600_ring_test, |
.ib_test = &r600_ib_test, |
.is_lockup = &evergreen_gpu_is_lockup, |
.is_lockup = &cayman_gfx_is_lockup, |
.vm_flush = &cayman_vm_flush, |
}, |
[CAYMAN_RING_TYPE_CP1_INDEX] = { |
1595,7 → 1665,7 |
// .cs_parse = &evergreen_cs_parse, |
.ring_test = &r600_ring_test, |
.ib_test = &r600_ib_test, |
.is_lockup = &evergreen_gpu_is_lockup, |
.is_lockup = &cayman_gfx_is_lockup, |
.vm_flush = &cayman_vm_flush, |
}, |
[CAYMAN_RING_TYPE_CP2_INDEX] = { |
1606,7 → 1676,7 |
// .cs_parse = &evergreen_cs_parse, |
.ring_test = &r600_ring_test, |
.ib_test = &r600_ib_test, |
.is_lockup = &evergreen_gpu_is_lockup, |
.is_lockup = &cayman_gfx_is_lockup, |
.vm_flush = &cayman_vm_flush, |
}, |
[R600_RING_TYPE_DMA_INDEX] = { |
1630,6 → 1700,15 |
.ib_test = &r600_dma_ib_test, |
.is_lockup = &cayman_dma_is_lockup, |
.vm_flush = &cayman_dma_vm_flush, |
}, |
[R600_RING_TYPE_UVD_INDEX] = { |
// .ib_execute = &r600_uvd_ib_execute, |
// .emit_fence = &r600_uvd_fence_emit, |
// .emit_semaphore = &cayman_uvd_semaphore_emit, |
// .cs_parse = &radeon_uvd_cs_parse, |
// .ring_test = &r600_uvd_ring_test, |
// .ib_test = &r600_uvd_ib_test, |
// .is_lockup = &radeon_ring_test_lockup, |
} |
}, |
.irq = { |
1674,6 → 1753,7 |
.get_pcie_lanes = NULL, |
.set_pcie_lanes = NULL, |
.set_clock_gating = NULL, |
.set_uvd_clocks = &sumo_set_uvd_clocks, |
}, |
.pflip = { |
// .pre_page_flip = &evergreen_pre_page_flip, |
1692,6 → 1772,8 |
// .ioctl_wait_idle = r600_ioctl_wait_idle, |
.gui_idle = &r600_gui_idle, |
.mc_wait_for_idle = &evergreen_mc_wait_for_idle, |
.get_xclk = &si_get_xclk, |
.get_gpu_clock_counter = &si_get_gpu_clock_counter, |
.gart = { |
.tlb_flush = &si_pcie_gart_tlb_flush, |
.set_page = &rs600_gart_set_page, |
1711,7 → 1793,7 |
.cs_parse = NULL, |
.ring_test = &r600_ring_test, |
.ib_test = &r600_ib_test, |
.is_lockup = &si_gpu_is_lockup, |
.is_lockup = &si_gfx_is_lockup, |
.vm_flush = &si_vm_flush, |
}, |
[CAYMAN_RING_TYPE_CP1_INDEX] = { |
1722,7 → 1804,7 |
.cs_parse = NULL, |
.ring_test = &r600_ring_test, |
.ib_test = &r600_ib_test, |
.is_lockup = &si_gpu_is_lockup, |
.is_lockup = &si_gfx_is_lockup, |
.vm_flush = &si_vm_flush, |
}, |
[CAYMAN_RING_TYPE_CP2_INDEX] = { |
1733,7 → 1815,7 |
.cs_parse = NULL, |
.ring_test = &r600_ring_test, |
.ib_test = &r600_ib_test, |
.is_lockup = &si_gpu_is_lockup, |
.is_lockup = &si_gfx_is_lockup, |
.vm_flush = &si_vm_flush, |
}, |
[R600_RING_TYPE_DMA_INDEX] = { |
1744,7 → 1826,7 |
.cs_parse = NULL, |
.ring_test = &r600_dma_ring_test, |
.ib_test = &r600_dma_ib_test, |
.is_lockup = &cayman_dma_is_lockup, |
.is_lockup = &si_dma_is_lockup, |
.vm_flush = &si_dma_vm_flush, |
}, |
[CAYMAN_RING_TYPE_DMA1_INDEX] = { |
1755,8 → 1837,17 |
.cs_parse = NULL, |
.ring_test = &r600_dma_ring_test, |
.ib_test = &r600_dma_ib_test, |
.is_lockup = &cayman_dma_is_lockup, |
.is_lockup = &si_dma_is_lockup, |
.vm_flush = &si_dma_vm_flush, |
}, |
[R600_RING_TYPE_UVD_INDEX] = { |
// .ib_execute = &r600_uvd_ib_execute, |
// .emit_fence = &r600_uvd_fence_emit, |
// .emit_semaphore = &cayman_uvd_semaphore_emit, |
// .cs_parse = &radeon_uvd_cs_parse, |
// .ring_test = &r600_uvd_ring_test, |
// .ib_test = &r600_uvd_ib_test, |
// .is_lockup = &radeon_ring_test_lockup, |
} |
}, |
.irq = { |
1801,6 → 1892,7 |
.get_pcie_lanes = NULL, |
.set_pcie_lanes = NULL, |
.set_clock_gating = NULL, |
// .set_uvd_clocks = &si_set_uvd_clocks, |
}, |
.pflip = { |
// .pre_page_flip = &evergreen_pre_page_flip, |
1829,6 → 1921,8 |
else |
rdev->num_crtc = 2; |
rdev->has_uvd = false; |
switch (rdev->family) { |
case CHIP_R100: |
case CHIP_RV100: |
1893,10 → 1987,15 |
case CHIP_RV635: |
case CHIP_RV670: |
rdev->asic = &r600_asic; |
if (rdev->family == CHIP_R600) |
rdev->has_uvd = false; |
else |
rdev->has_uvd = true; |
break; |
case CHIP_RS780: |
case CHIP_RS880: |
rdev->asic = &rs780_asic; |
rdev->has_uvd = true; |
break; |
case CHIP_RV770: |
case CHIP_RV730: |
1903,6 → 2002,7 |
case CHIP_RV710: |
case CHIP_RV740: |
rdev->asic = &rv770_asic; |
rdev->has_uvd = true; |
break; |
case CHIP_CEDAR: |
case CHIP_REDWOOD: |
1915,11 → 2015,13 |
else |
rdev->num_crtc = 6; |
rdev->asic = &evergreen_asic; |
rdev->has_uvd = true; |
break; |
case CHIP_PALM: |
case CHIP_SUMO: |
case CHIP_SUMO2: |
rdev->asic = &sumo_asic; |
rdev->has_uvd = true; |
break; |
case CHIP_BARTS: |
case CHIP_TURKS: |
1930,23 → 2032,37 |
else |
rdev->num_crtc = 6; |
rdev->asic = &btc_asic; |
rdev->has_uvd = true; |
break; |
case CHIP_CAYMAN: |
rdev->asic = &cayman_asic; |
/* set num crtcs */ |
rdev->num_crtc = 6; |
rdev->has_uvd = true; |
break; |
case CHIP_ARUBA: |
rdev->asic = &trinity_asic; |
/* set num crtcs */ |
rdev->num_crtc = 4; |
rdev->has_uvd = true; |
break; |
case CHIP_TAHITI: |
case CHIP_PITCAIRN: |
case CHIP_VERDE: |
case CHIP_OLAND: |
case CHIP_HAINAN: |
rdev->asic = &si_asic; |
/* set num crtcs */ |
if (rdev->family == CHIP_HAINAN) |
rdev->num_crtc = 0; |
else if (rdev->family == CHIP_OLAND) |
rdev->num_crtc = 2; |
else |
rdev->num_crtc = 6; |
if (rdev->family == CHIP_HAINAN) |
rdev->has_uvd = false; |
else |
rdev->has_uvd = true; |
break; |
default: |
/* FIXME: not supported yet */ |
/drivers/video/drm/radeon/radeon_asic.h |
---|
319,7 → 319,7 |
bool emit_wait); |
void r600_dma_ring_ib_execute(struct radeon_device *rdev, struct radeon_ib *ib); |
bool r600_dma_is_lockup(struct radeon_device *rdev, struct radeon_ring *ring); |
bool r600_gpu_is_lockup(struct radeon_device *rdev, struct radeon_ring *cp); |
bool r600_gfx_is_lockup(struct radeon_device *rdev, struct radeon_ring *cp); |
int r600_asic_reset(struct radeon_device *rdev); |
int r600_set_surface_reg(struct radeon_device *rdev, int reg, |
uint32_t tiling_flags, uint32_t pitch, |
330,6 → 330,7 |
void r600_ring_ib_execute(struct radeon_device *rdev, struct radeon_ib *ib); |
int r600_ring_test(struct radeon_device *rdev, struct radeon_ring *cp); |
int r600_dma_ring_test(struct radeon_device *rdev, struct radeon_ring *cp); |
int r600_uvd_ring_test(struct radeon_device *rdev, struct radeon_ring *ring); |
int r600_copy_blit(struct radeon_device *rdev, |
uint64_t src_offset, uint64_t dst_offset, |
unsigned num_gpu_pages, struct radeon_fence **fence); |
346,6 → 347,8 |
extern void r600_pm_misc(struct radeon_device *rdev); |
extern void r600_pm_init_profile(struct radeon_device *rdev); |
extern void rs780_pm_init_profile(struct radeon_device *rdev); |
extern uint32_t rs780_mc_rreg(struct radeon_device *rdev, uint32_t reg); |
extern void rs780_mc_wreg(struct radeon_device *rdev, uint32_t reg, uint32_t v); |
extern void r600_pm_get_dynpm_state(struct radeon_device *rdev); |
extern void r600_set_pcie_lanes(struct radeon_device *rdev, int lanes); |
extern int r600_get_pcie_lanes(struct radeon_device *rdev); |
373,11 → 376,12 |
void r600_rlc_stop(struct radeon_device *rdev); |
/* r600 audio */ |
int r600_audio_init(struct radeon_device *rdev); |
void r600_audio_set_clock(struct drm_encoder *encoder, int clock); |
struct r600_audio r600_audio_status(struct radeon_device *rdev); |
void r600_audio_fini(struct radeon_device *rdev); |
int r600_hdmi_buffer_status_changed(struct drm_encoder *encoder); |
void r600_hdmi_update_audio_settings(struct drm_encoder *encoder); |
void r600_hdmi_enable(struct drm_encoder *encoder, bool enable); |
void r600_hdmi_setmode(struct drm_encoder *encoder, struct drm_display_mode *mode); |
/* r600 blit */ |
int r600_blit_prepare_copy(struct radeon_device *rdev, unsigned num_gpu_pages, |
struct radeon_fence **fence, struct radeon_sa_bo **vb, |
389,8 → 393,22 |
unsigned num_gpu_pages, |
struct radeon_sa_bo *vb); |
int r600_mc_wait_for_idle(struct radeon_device *rdev); |
uint64_t r600_get_gpu_clock(struct radeon_device *rdev); |
u32 r600_get_xclk(struct radeon_device *rdev); |
uint64_t r600_get_gpu_clock_counter(struct radeon_device *rdev); |
/* uvd */ |
int r600_uvd_init(struct radeon_device *rdev); |
int r600_uvd_rbc_start(struct radeon_device *rdev); |
void r600_uvd_rbc_stop(struct radeon_device *rdev); |
int r600_uvd_ib_test(struct radeon_device *rdev, struct radeon_ring *ring); |
void r600_uvd_fence_emit(struct radeon_device *rdev, |
struct radeon_fence *fence); |
void r600_uvd_semaphore_emit(struct radeon_device *rdev, |
struct radeon_ring *ring, |
struct radeon_semaphore *semaphore, |
bool emit_wait); |
void r600_uvd_ib_execute(struct radeon_device *rdev, struct radeon_ib *ib); |
/* |
* rv770,rv730,rv710,rv740 |
*/ |
407,6 → 425,9 |
uint64_t src_offset, uint64_t dst_offset, |
unsigned num_gpu_pages, |
struct radeon_fence **fence); |
u32 rv770_get_xclk(struct radeon_device *rdev); |
int rv770_uvd_resume(struct radeon_device *rdev); |
int rv770_set_uvd_clocks(struct radeon_device *rdev, u32 vclk, u32 dclk); |
/* |
* evergreen |
422,7 → 443,8 |
void evergreen_fini(struct radeon_device *rdev); |
int evergreen_suspend(struct radeon_device *rdev); |
int evergreen_resume(struct radeon_device *rdev); |
bool evergreen_gpu_is_lockup(struct radeon_device *rdev, struct radeon_ring *cp); |
bool evergreen_gfx_is_lockup(struct radeon_device *rdev, struct radeon_ring *cp); |
bool evergreen_dma_is_lockup(struct radeon_device *rdev, struct radeon_ring *cp); |
int evergreen_asic_reset(struct radeon_device *rdev); |
void evergreen_bandwidth_update(struct radeon_device *rdev); |
void evergreen_ring_ib_execute(struct radeon_device *rdev, struct radeon_ib *ib); |
441,6 → 463,8 |
extern void evergreen_pm_finish(struct radeon_device *rdev); |
extern void sumo_pm_init_profile(struct radeon_device *rdev); |
extern void btc_pm_init_profile(struct radeon_device *rdev); |
int sumo_set_uvd_clocks(struct radeon_device *rdev, u32 vclk, u32 dclk); |
int evergreen_set_uvd_clocks(struct radeon_device *rdev, u32 vclk, u32 dclk); |
extern void evergreen_pre_page_flip(struct radeon_device *rdev, int crtc); |
extern u32 evergreen_page_flip(struct radeon_device *rdev, int crtc, u64 crtc_base); |
extern void evergreen_post_page_flip(struct radeon_device *rdev, int crtc); |
456,6 → 480,8 |
uint64_t src_offset, uint64_t dst_offset, |
unsigned num_gpu_pages, |
struct radeon_fence **fence); |
void evergreen_hdmi_enable(struct drm_encoder *encoder, bool enable); |
void evergreen_hdmi_setmode(struct drm_encoder *encoder, struct drm_display_mode *mode); |
/* |
* cayman |
462,6 → 488,10 |
*/ |
void cayman_fence_ring_emit(struct radeon_device *rdev, |
struct radeon_fence *fence); |
void cayman_uvd_semaphore_emit(struct radeon_device *rdev, |
struct radeon_ring *ring, |
struct radeon_semaphore *semaphore, |
bool emit_wait); |
void cayman_pcie_gart_tlb_flush(struct radeon_device *rdev); |
int cayman_init(struct radeon_device *rdev); |
void cayman_fini(struct radeon_device *rdev); |
473,7 → 503,9 |
void cayman_vm_fini(struct radeon_device *rdev); |
void cayman_vm_flush(struct radeon_device *rdev, int ridx, struct radeon_vm *vm); |
uint32_t cayman_vm_page_flags(struct radeon_device *rdev, uint32_t flags); |
void cayman_vm_set_page(struct radeon_device *rdev, uint64_t pe, |
void cayman_vm_set_page(struct radeon_device *rdev, |
struct radeon_ib *ib, |
uint64_t pe, |
uint64_t addr, unsigned count, |
uint32_t incr, uint32_t flags); |
int evergreen_ib_parse(struct radeon_device *rdev, struct radeon_ib *ib); |
480,6 → 512,7 |
int evergreen_dma_ib_parse(struct radeon_device *rdev, struct radeon_ib *ib); |
void cayman_dma_ring_ib_execute(struct radeon_device *rdev, |
struct radeon_ib *ib); |
bool cayman_gfx_is_lockup(struct radeon_device *rdev, struct radeon_ring *ring); |
bool cayman_dma_is_lockup(struct radeon_device *rdev, struct radeon_ring *ring); |
void cayman_dma_vm_flush(struct radeon_device *rdev, int ridx, struct radeon_vm *vm); |
496,7 → 529,8 |
void si_fini(struct radeon_device *rdev); |
int si_suspend(struct radeon_device *rdev); |
int si_resume(struct radeon_device *rdev); |
bool si_gpu_is_lockup(struct radeon_device *rdev, struct radeon_ring *cp); |
bool si_gfx_is_lockup(struct radeon_device *rdev, struct radeon_ring *cp); |
bool si_dma_is_lockup(struct radeon_device *rdev, struct radeon_ring *cp); |
int si_asic_reset(struct radeon_device *rdev); |
void si_ring_ib_execute(struct radeon_device *rdev, struct radeon_ib *ib); |
int si_irq_set(struct radeon_device *rdev); |
503,16 → 537,20 |
int si_irq_process(struct radeon_device *rdev); |
int si_vm_init(struct radeon_device *rdev); |
void si_vm_fini(struct radeon_device *rdev); |
void si_vm_set_page(struct radeon_device *rdev, uint64_t pe, |
void si_vm_set_page(struct radeon_device *rdev, |
struct radeon_ib *ib, |
uint64_t pe, |
uint64_t addr, unsigned count, |
uint32_t incr, uint32_t flags); |
void si_vm_flush(struct radeon_device *rdev, int ridx, struct radeon_vm *vm); |
int si_ib_parse(struct radeon_device *rdev, struct radeon_ib *ib); |
uint64_t si_get_gpu_clock(struct radeon_device *rdev); |
int si_copy_dma(struct radeon_device *rdev, |
uint64_t src_offset, uint64_t dst_offset, |
unsigned num_gpu_pages, |
struct radeon_fence **fence); |
void si_dma_vm_flush(struct radeon_device *rdev, int ridx, struct radeon_vm *vm); |
u32 si_get_xclk(struct radeon_device *rdev); |
uint64_t si_get_gpu_clock_counter(struct radeon_device *rdev); |
int si_set_uvd_clocks(struct radeon_device *rdev, u32 vclk, u32 dclk); |
#endif |
/drivers/video/drm/radeon/radeon_atombios.c |
---|
2028,6 → 2028,8 |
num_modes = power_info->info.ucNumOfPowerModeEntries; |
if (num_modes > ATOM_MAX_NUMBEROF_POWER_BLOCK) |
num_modes = ATOM_MAX_NUMBEROF_POWER_BLOCK; |
if (num_modes == 0) |
return state_index; |
rdev->pm.power_state = kzalloc(sizeof(struct radeon_power_state) * num_modes, GFP_KERNEL); |
if (!rdev->pm.power_state) |
return state_index; |
2307,7 → 2309,7 |
rdev->pm.default_power_state_index = state_index; |
rdev->pm.power_state[state_index].default_clock_mode = |
&rdev->pm.power_state[state_index].clock_info[mode_index - 1]; |
if (ASIC_IS_DCE5(rdev) && !(rdev->flags & RADEON_IS_IGP)) { |
if ((rdev->family >= CHIP_BARTS) && !(rdev->flags & RADEON_IS_IGP)) { |
/* NI chips post without MC ucode, so default clocks are strobe mode only */ |
rdev->pm.default_sclk = rdev->pm.power_state[state_index].clock_info[0].sclk; |
rdev->pm.default_mclk = rdev->pm.power_state[state_index].clock_info[0].mclk; |
2345,7 → 2347,7 |
sclk |= clock_info->rs780.ucLowEngineClockHigh << 16; |
rdev->pm.power_state[state_index].clock_info[mode_index].sclk = sclk; |
} |
} else if (ASIC_IS_DCE6(rdev)) { |
} else if (rdev->family >= CHIP_TAHITI) { |
sclk = le16_to_cpu(clock_info->si.usEngineClockLow); |
sclk |= clock_info->si.ucEngineClockHigh << 16; |
mclk = le16_to_cpu(clock_info->si.usMemoryClockLow); |
2358,7 → 2360,7 |
le16_to_cpu(clock_info->si.usVDDC); |
rdev->pm.power_state[state_index].clock_info[mode_index].voltage.vddci = |
le16_to_cpu(clock_info->si.usVDDCI); |
} else if (ASIC_IS_DCE4(rdev)) { |
} else if (rdev->family >= CHIP_CEDAR) { |
sclk = le16_to_cpu(clock_info->evergreen.usEngineClockLow); |
sclk |= clock_info->evergreen.ucEngineClockHigh << 16; |
mclk = le16_to_cpu(clock_info->evergreen.usMemoryClockLow); |
2432,6 → 2434,8 |
power_info = (union power_info *)(mode_info->atom_context->bios + data_offset); |
radeon_atombios_add_pplib_thermal_controller(rdev, &power_info->pplib.sThermalController); |
if (power_info->pplib.ucNumStates == 0) |
return state_index; |
rdev->pm.power_state = kzalloc(sizeof(struct radeon_power_state) * |
power_info->pplib.ucNumStates, GFP_KERNEL); |
if (!rdev->pm.power_state) |
2514,6 → 2518,7 |
int index = GetIndexIntoMasterTable(DATA, PowerPlayInfo); |
u16 data_offset; |
u8 frev, crev; |
u8 *power_state_offset; |
if (!atom_parse_data_header(mode_info->atom_context, index, NULL, |
&frev, &crev, &data_offset)) |
2530,15 → 2535,17 |
non_clock_info_array = (struct _NonClockInfoArray *) |
(mode_info->atom_context->bios + data_offset + |
le16_to_cpu(power_info->pplib.usNonClockInfoArrayOffset)); |
if (state_array->ucNumEntries == 0) |
return state_index; |
rdev->pm.power_state = kzalloc(sizeof(struct radeon_power_state) * |
state_array->ucNumEntries, GFP_KERNEL); |
if (!rdev->pm.power_state) |
return state_index; |
power_state_offset = (u8 *)state_array->states; |
for (i = 0; i < state_array->ucNumEntries; i++) { |
mode_index = 0; |
power_state = (union pplib_power_state *)&state_array->states[i]; |
/* XXX this might be an inagua bug... */ |
non_clock_array_index = i; /* power_state->v2.nonClockInfoIndex */ |
power_state = (union pplib_power_state *)power_state_offset; |
non_clock_array_index = power_state->v2.nonClockInfoIndex; |
non_clock_info = (struct _ATOM_PPLIB_NONCLOCK_INFO *) |
&non_clock_info_array->nonClockInfo[non_clock_array_index]; |
rdev->pm.power_state[i].clock_info = kzalloc(sizeof(struct radeon_pm_clock_info) * |
2550,9 → 2557,6 |
if (power_state->v2.ucNumDPMLevels) { |
for (j = 0; j < power_state->v2.ucNumDPMLevels; j++) { |
clock_array_index = power_state->v2.clockInfoIndex[j]; |
/* XXX this might be an inagua bug... */ |
if (clock_array_index >= clock_info_array->ucNumEntries) |
continue; |
clock_info = (union pplib_clock_info *) |
&clock_info_array->clockInfo[clock_array_index * clock_info_array->ucEntrySize]; |
valid = radeon_atombios_parse_pplib_clock_info(rdev, |
2574,6 → 2578,7 |
non_clock_info); |
state_index++; |
} |
power_state_offset += 2 + power_state->v2.ucNumDPMLevels; |
} |
/* if multiple clock modes, mark the lowest as no display */ |
for (i = 0; i < state_index; i++) { |
2620,7 → 2625,9 |
default: |
break; |
} |
} else { |
} |
if (state_index == 0) { |
rdev->pm.power_state = kzalloc(sizeof(struct radeon_power_state), GFP_KERNEL); |
if (rdev->pm.power_state) { |
rdev->pm.power_state[0].clock_info = |
2654,6 → 2661,111 |
rdev->pm.current_vddc = 0; |
} |
union get_clock_dividers { |
struct _COMPUTE_MEMORY_ENGINE_PLL_PARAMETERS v1; |
struct _COMPUTE_MEMORY_ENGINE_PLL_PARAMETERS_V2 v2; |
struct _COMPUTE_MEMORY_ENGINE_PLL_PARAMETERS_V3 v3; |
struct _COMPUTE_MEMORY_ENGINE_PLL_PARAMETERS_V4 v4; |
struct _COMPUTE_MEMORY_ENGINE_PLL_PARAMETERS_V5 v5; |
}; |
int radeon_atom_get_clock_dividers(struct radeon_device *rdev, |
u8 clock_type, |
u32 clock, |
bool strobe_mode, |
struct atom_clock_dividers *dividers) |
{ |
union get_clock_dividers args; |
int index = GetIndexIntoMasterTable(COMMAND, ComputeMemoryEnginePLL); |
u8 frev, crev; |
memset(&args, 0, sizeof(args)); |
memset(dividers, 0, sizeof(struct atom_clock_dividers)); |
if (!atom_parse_cmd_header(rdev->mode_info.atom_context, index, &frev, &crev)) |
return -EINVAL; |
switch (crev) { |
case 1: |
/* r4xx, r5xx */ |
args.v1.ucAction = clock_type; |
args.v1.ulClock = cpu_to_le32(clock); /* 10 khz */ |
atom_execute_table(rdev->mode_info.atom_context, index, (uint32_t *)&args); |
dividers->post_div = args.v1.ucPostDiv; |
dividers->fb_div = args.v1.ucFbDiv; |
dividers->enable_post_div = true; |
break; |
case 2: |
case 3: |
/* r6xx, r7xx, evergreen, ni */ |
if (rdev->family <= CHIP_RV770) { |
args.v2.ucAction = clock_type; |
args.v2.ulClock = cpu_to_le32(clock); /* 10 khz */ |
atom_execute_table(rdev->mode_info.atom_context, index, (uint32_t *)&args); |
dividers->post_div = args.v2.ucPostDiv; |
dividers->fb_div = le16_to_cpu(args.v2.usFbDiv); |
dividers->ref_div = args.v2.ucAction; |
if (rdev->family == CHIP_RV770) { |
dividers->enable_post_div = (le32_to_cpu(args.v2.ulClock) & (1 << 24)) ? |
true : false; |
dividers->vco_mode = (le32_to_cpu(args.v2.ulClock) & (1 << 25)) ? 1 : 0; |
} else |
dividers->enable_post_div = (dividers->fb_div & 1) ? true : false; |
} else { |
if (clock_type == COMPUTE_ENGINE_PLL_PARAM) { |
args.v3.ulClockParams = cpu_to_le32((clock_type << 24) | clock); |
atom_execute_table(rdev->mode_info.atom_context, index, (uint32_t *)&args); |
dividers->post_div = args.v3.ucPostDiv; |
dividers->enable_post_div = (args.v3.ucCntlFlag & |
ATOM_PLL_CNTL_FLAG_PLL_POST_DIV_EN) ? true : false; |
dividers->enable_dithen = (args.v3.ucCntlFlag & |
ATOM_PLL_CNTL_FLAG_FRACTION_DISABLE) ? false : true; |
dividers->fb_div = le16_to_cpu(args.v3.ulFbDiv.usFbDiv); |
dividers->frac_fb_div = le16_to_cpu(args.v3.ulFbDiv.usFbDivFrac); |
dividers->ref_div = args.v3.ucRefDiv; |
dividers->vco_mode = (args.v3.ucCntlFlag & |
ATOM_PLL_CNTL_FLAG_MPLL_VCO_MODE) ? 1 : 0; |
} else { |
args.v5.ulClockParams = cpu_to_le32((clock_type << 24) | clock); |
if (strobe_mode) |
args.v5.ucInputFlag = ATOM_PLL_INPUT_FLAG_PLL_STROBE_MODE_EN; |
atom_execute_table(rdev->mode_info.atom_context, index, (uint32_t *)&args); |
dividers->post_div = args.v5.ucPostDiv; |
dividers->enable_post_div = (args.v5.ucCntlFlag & |
ATOM_PLL_CNTL_FLAG_PLL_POST_DIV_EN) ? true : false; |
dividers->enable_dithen = (args.v5.ucCntlFlag & |
ATOM_PLL_CNTL_FLAG_FRACTION_DISABLE) ? false : true; |
dividers->whole_fb_div = le16_to_cpu(args.v5.ulFbDiv.usFbDiv); |
dividers->frac_fb_div = le16_to_cpu(args.v5.ulFbDiv.usFbDivFrac); |
dividers->ref_div = args.v5.ucRefDiv; |
dividers->vco_mode = (args.v5.ucCntlFlag & |
ATOM_PLL_CNTL_FLAG_MPLL_VCO_MODE) ? 1 : 0; |
} |
} |
break; |
case 4: |
/* fusion */ |
args.v4.ulClock = cpu_to_le32(clock); /* 10 khz */ |
atom_execute_table(rdev->mode_info.atom_context, index, (uint32_t *)&args); |
dividers->post_div = args.v4.ucPostDiv; |
dividers->real_clock = le32_to_cpu(args.v4.ulClock); |
break; |
default: |
return -EINVAL; |
} |
return 0; |
} |
void radeon_atom_set_clock_gating(struct radeon_device *rdev, int enable) |
{ |
DYNAMIC_CLOCK_GATING_PS_ALLOCATION args; |
/drivers/video/drm/radeon/radeon_bios.c |
---|
91,11 → 91,9 |
} |
rdev->bios = kmalloc(size, GFP_KERNEL); |
if (rdev->bios == NULL) { |
// pci_unmap_rom(rdev->pdev, bios); |
return false; |
} |
memcpy(rdev->bios, bios, size); |
// pci_unmap_rom(rdev->pdev, bios); |
return true; |
} |
221,6 → 219,7 |
/* enable the rom */ |
WREG32(R600_BUS_CNTL, (bus_cntl & ~R600_BIOS_ROM_DIS)); |
if (!ASIC_IS_NODCE(rdev)) { |
/* Disable VGA mode */ |
WREG32(AVIVO_D1VGA_CONTROL, |
(d1vga_control & ~(AVIVO_DVGA_CONTROL_MODE_ENABLE | |
230,6 → 229,7 |
AVIVO_DVGA_CONTROL_TIMING_SELECT))); |
WREG32(AVIVO_VGA_RENDER_CONTROL, |
(vga_render_control & ~AVIVO_VGA_VSTATUS_CNTL_MASK)); |
} |
WREG32(R600_ROM_CNTL, rom_cntl | R600_SCK_OVERWRITE); |
r = radeon_read_bios(rdev); |
236,9 → 236,11 |
/* restore regs */ |
WREG32(R600_BUS_CNTL, bus_cntl); |
if (!ASIC_IS_NODCE(rdev)) { |
WREG32(AVIVO_D1VGA_CONTROL, d1vga_control); |
WREG32(AVIVO_D2VGA_CONTROL, d2vga_control); |
WREG32(AVIVO_VGA_RENDER_CONTROL, vga_render_control); |
} |
WREG32(R600_ROM_CNTL, rom_cntl); |
return r; |
} |
/drivers/video/drm/radeon/radeon_combios.c |
---|
970,6 → 970,15 |
found = 1; |
} |
/* quirks */ |
/* Radeon 9100 (R200) */ |
if ((dev->pdev->device == 0x514D) && |
(dev->pdev->subsystem_vendor == 0x174B) && |
(dev->pdev->subsystem_device == 0x7149)) { |
/* vbios value is bad, use the default */ |
found = 0; |
} |
if (!found) /* fallback to defaults */ |
radeon_legacy_get_primary_dac_info_from_table(rdev, p_dac); |
2470,6 → 2479,14 |
1), |
ATOM_DEVICE_CRT1_SUPPORT); |
} |
/* RV100 board with external TDMS bit mis-set. |
* Actually uses internal TMDS, clear the bit. |
*/ |
if (dev->pdev->device == 0x5159 && |
dev->pdev->subsystem_vendor == 0x1014 && |
dev->pdev->subsystem_device == 0x029A) { |
tmp &= ~(1 << 4); |
} |
if ((tmp >> 4) & 0x1) { |
devices |= ATOM_DEVICE_DFP2_SUPPORT; |
radeon_add_legacy_encoder(dev, |
/drivers/video/drm/radeon/radeon_connectors.c |
---|
615,8 → 615,6 |
struct drm_encoder *encoder = radeon_best_single_encoder(connector); |
enum drm_connector_status ret = connector_status_disconnected; |
ENTER(); |
if (encoder) { |
struct radeon_encoder *radeon_encoder = to_radeon_encoder(encoder); |
struct drm_display_mode *native_mode = &radeon_encoder->native_mode; |
641,7 → 639,6 |
/* check acpi lid status ??? */ |
radeon_connector_update_scratch_regs(connector, ret); |
LEAVE(); |
return ret; |
} |
949,7 → 946,6 |
enum drm_connector_status ret = connector_status_disconnected; |
bool dret = false, broken_edid = false; |
if (!force && radeon_check_hpd_status_unchanged(connector)) |
return connector->status; |
1370,8 → 1366,6 |
struct radeon_connector_atom_dig *radeon_dig_connector = radeon_connector->con_priv; |
struct drm_encoder *encoder = radeon_best_single_encoder(connector); |
dbgprintf("%s radeon_connector %p encoder %p\n", |
__FUNCTION__, radeon_connector, encoder); |
#if DISABLE_DP |
connector->status = connector_status_disconnected; |
1401,7 → 1395,6 |
if (!radeon_dig_connector->edp_on) |
atombios_set_edp_panel_power(connector, |
ATOM_TRANSMITTER_ACTION_POWER_ON); |
dbgprintf("check eDP\n"); |
if (radeon_dp_getdpcd(radeon_connector)) |
ret = connector_status_connected; |
if (!radeon_dig_connector->edp_on) |
1444,7 → 1437,6 |
} |
radeon_connector_update_scratch_regs(connector, ret); |
LEAVE(); |
return ret; |
} |
1879,7 → 1871,7 |
connector->polled = DRM_CONNECTOR_POLL_HPD; |
connector->display_info.subpixel_order = subpixel_order; |
// drm_sysfs_connector_add(connector); |
drm_sysfs_connector_add(connector); |
return; |
failed: |
2036,5 → 2028,5 |
} else |
connector->polled = DRM_CONNECTOR_POLL_HPD; |
connector->display_info.subpixel_order = subpixel_order; |
// drm_sysfs_connector_add(connector); |
drm_sysfs_connector_add(connector); |
} |
/drivers/video/drm/radeon/radeon_device.c |
---|
59,8 → 59,8 |
int radeon_pcie_gen2 = 0; |
int radeon_disp_priority = 0; |
int radeon_lockup_timeout = 10000; |
int radeon_fastfb = 0; |
int irq_override = 0; |
143,10 → 143,48 |
"TAHITI", |
"PITCAIRN", |
"VERDE", |
"OLAND", |
"HAINAN", |
"LAST", |
}; |
/** |
* radeon_program_register_sequence - program an array of registers. |
* |
* @rdev: radeon_device pointer |
* @registers: pointer to the register array |
* @array_size: size of the register array |
* |
* Programs an array or registers with and and or masks. |
* This is a helper for setting golden registers. |
*/ |
void radeon_program_register_sequence(struct radeon_device *rdev, |
const u32 *registers, |
const u32 array_size) |
{ |
u32 tmp, reg, and_mask, or_mask; |
int i; |
if (array_size % 3) |
return; |
for (i = 0; i < array_size; i +=3) { |
reg = registers[i + 0]; |
and_mask = registers[i + 1]; |
or_mask = registers[i + 2]; |
if (and_mask == 0xffffffff) { |
tmp = or_mask; |
} else { |
tmp = RREG32(reg); |
tmp &= ~and_mask; |
tmp |= or_mask; |
} |
WREG32(reg, tmp); |
} |
} |
/** |
* radeon_surface_init - Clear GPU surface registers. |
* |
* @rdev: radeon_device pointer |
253,16 → 291,6 |
*/ |
void radeon_wb_disable(struct radeon_device *rdev) |
{ |
int r; |
if (rdev->wb.wb_obj) { |
r = radeon_bo_reserve(rdev->wb.wb_obj, false); |
if (unlikely(r != 0)) |
return; |
radeon_bo_kunmap(rdev->wb.wb_obj); |
radeon_bo_unpin(rdev->wb.wb_obj); |
radeon_bo_unreserve(rdev->wb.wb_obj); |
} |
rdev->wb.enabled = false; |
} |
304,7 → 332,6 |
dev_warn(rdev->dev, "(%d) create WB bo failed\n", r); |
return r; |
} |
} |
r = radeon_bo_reserve(rdev->wb.wb_obj, false); |
if (unlikely(r != 0)) { |
radeon_wb_fini(rdev); |
325,6 → 352,7 |
radeon_wb_fini(rdev); |
return r; |
} |
} |
/* clear wb memory */ |
memset((char *)rdev->wb.wb, 0, RADEON_GPU_PAGE_SIZE); |
405,7 → 433,7 |
uint64_t limit = (uint64_t)radeon_vram_limit << 20; |
mc->vram_start = base; |
if (mc->mc_vram_size > (0xFFFFFFFF - base + 1)) { |
if (mc->mc_vram_size > (rdev->mc.mc_mask - base + 1)) { |
dev_warn(rdev->dev, "limiting VRAM to PCI aperture size\n"); |
mc->real_vram_size = mc->aper_size; |
mc->mc_vram_size = mc->aper_size; |
440,7 → 468,7 |
{ |
u64 size_af, size_bf; |
size_af = ((0xFFFFFFFF - mc->vram_end) + mc->gtt_base_align) & ~mc->gtt_base_align; |
size_af = ((rdev->mc.mc_mask - mc->vram_end) + mc->gtt_base_align) & ~mc->gtt_base_align; |
size_bf = mc->vram_start & ~mc->gtt_base_align; |
if (size_bf > size_af) { |
if (mc->gtt_size > size_bf) { |
476,19 → 504,21 |
{ |
uint32_t reg; |
if (ASIC_IS_NODCE(rdev)) |
goto check_memsize; |
/* first check CRTCs */ |
if (ASIC_IS_DCE41(rdev)) { |
if (ASIC_IS_DCE4(rdev)) { |
reg = RREG32(EVERGREEN_CRTC_CONTROL + EVERGREEN_CRTC0_REGISTER_OFFSET) | |
RREG32(EVERGREEN_CRTC_CONTROL + EVERGREEN_CRTC1_REGISTER_OFFSET); |
if (reg & EVERGREEN_CRTC_MASTER_EN) |
return true; |
} else if (ASIC_IS_DCE4(rdev)) { |
reg = RREG32(EVERGREEN_CRTC_CONTROL + EVERGREEN_CRTC0_REGISTER_OFFSET) | |
RREG32(EVERGREEN_CRTC_CONTROL + EVERGREEN_CRTC1_REGISTER_OFFSET) | |
RREG32(EVERGREEN_CRTC_CONTROL + EVERGREEN_CRTC2_REGISTER_OFFSET) | |
RREG32(EVERGREEN_CRTC_CONTROL + EVERGREEN_CRTC3_REGISTER_OFFSET) | |
RREG32(EVERGREEN_CRTC_CONTROL + EVERGREEN_CRTC4_REGISTER_OFFSET) | |
if (rdev->num_crtc >= 4) { |
reg |= RREG32(EVERGREEN_CRTC_CONTROL + EVERGREEN_CRTC2_REGISTER_OFFSET) | |
RREG32(EVERGREEN_CRTC_CONTROL + EVERGREEN_CRTC3_REGISTER_OFFSET); |
} |
if (rdev->num_crtc >= 6) { |
reg |= RREG32(EVERGREEN_CRTC_CONTROL + EVERGREEN_CRTC4_REGISTER_OFFSET) | |
RREG32(EVERGREEN_CRTC_CONTROL + EVERGREEN_CRTC5_REGISTER_OFFSET); |
} |
if (reg & EVERGREEN_CRTC_MASTER_EN) |
return true; |
} else if (ASIC_IS_AVIVO(rdev)) { |
505,6 → 535,7 |
} |
} |
check_memsize: |
/* then check MEM_SIZE, in case the crtcs are off */ |
if (rdev->family >= CHIP_R600) |
reg = RREG32(R600_CONFIG_MEMSIZE); |
797,6 → 828,11 |
atom_card_info->pll_write = cail_pll_write; |
rdev->mode_info.atom_context = atom_parse(atom_card_info, rdev->bios); |
if (!rdev->mode_info.atom_context) { |
radeon_atombios_fini(rdev); |
return -ENOMEM; |
} |
mutex_init(&rdev->mode_info.atom_context->mutex); |
radeon_atom_initialize_bios_scratch_regs(rdev->ddev); |
atom_allocate_fb_scratch(rdev->mode_info.atom_context); |
816,9 → 852,11 |
{ |
if (rdev->mode_info.atom_context) { |
kfree(rdev->mode_info.atom_context->scratch); |
} |
kfree(rdev->mode_info.atom_context); |
} |
rdev->mode_info.atom_context = NULL; |
kfree(rdev->mode_info.atom_card_info); |
rdev->mode_info.atom_card_info = NULL; |
} |
/* COMBIOS */ |
970,8 → 1008,8 |
mutex_init(&rdev->gem.mutex); |
mutex_init(&rdev->pm.mutex); |
mutex_init(&rdev->gpu_clock_mutex); |
init_rwsem(&rdev->pm.mclk_lock); |
init_rwsem(&rdev->exclusive_lock); |
// init_rwsem(&rdev->pm.mclk_lock); |
// init_rwsem(&rdev->exclusive_lock); |
init_waitqueue_head(&rdev->irq.vblank_queue); |
r = radeon_gem_init(rdev); |
if (r) |
1003,6 → 1041,17 |
radeon_agp_disable(rdev); |
} |
/* Set the internal MC address mask |
* This is the max address of the GPU's |
* internal address space. |
*/ |
if (rdev->family >= CHIP_CAYMAN) |
rdev->mc.mc_mask = 0xffffffffffULL; /* 40 bit MC */ |
else if (rdev->family >= CHIP_CEDAR) |
rdev->mc.mc_mask = 0xfffffffffULL; /* 36 bit MC */ |
else |
rdev->mc.mc_mask = 0xffffffffULL; /* 32 bit MC */ |
/* set DMA mask + need_dma32 flags. |
* PCIE - can handle 40-bits. |
* IGP - can handle 40-bits |
1121,7 → 1170,6 |
} |
radeon_restore_bios_scratch_regs(rdev); |
drm_helper_resume_force_mode(rdev->ddev); |
if (!r) { |
for (i = 0; i < RADEON_NUM_RINGS; ++i) { |
1165,7 → 1213,6 |
struct radeon_device *rdev; |
int r; |
ENTER(); |
rdev = kzalloc(sizeof(struct radeon_device), GFP_KERNEL); |
if (rdev == NULL) { |
1216,8 → 1263,6 |
static struct drm_device *dev; |
int ret; |
ENTER(); |
dev = kzalloc(sizeof(*dev), 0); |
if (!dev) |
return -ENOMEM; |
1259,8 → 1304,6 |
init_display(dev->dev_private, &usermode); |
LEAVE(); |
return 0; |
err_g4: |
1392,7 → 1435,7 |
if( radeon_modeset ) |
retval = set_user_mode((videomode_t*)inp); |
break; |
/* |
case SRV_GET_CAPS: |
retval = get_driver_caps((hwcaps_t*)inp); |
break; |
1409,7 → 1452,7 |
case SRV_BLIT_BITMAP: |
srv_blit_bitmap( inp[0], inp[1], inp[2], |
inp[3], inp[4], inp[5], inp[6]); |
*/ |
}; |
return retval; |
1438,7 → 1481,7 |
if(!dbg_open(log)) |
{ |
strcpy(log, "/TMP1/1/atikms.log"); |
strcpy(log, "/TMP1/1/ati.log"); |
if(!dbg_open(log)) |
{ |
1446,8 → 1489,10 |
return 0; |
}; |
} |
dbgprintf("Radeon RC13 cmdline %s\n", cmdline); |
dbgprintf("Radeon v3.10 preview-1 cmdline %s\n", cmdline); |
cpu_detect(); |
enum_pci_devices(); |
ent = find_pci_device(&device, pciidlist); |
1461,6 → 1506,8 |
dbgprintf("device %x:%x\n", device.pci_dev.vendor, |
device.pci_dev.device); |
drm_global_init(); |
err = drm_get_dev(&device.pci_dev, ent); |
rdev = rdisplay->ddev->dev_private; |
1496,12 → 1543,3 |
return ret; |
} |
unsigned int hweight32(unsigned int w) |
{ |
unsigned int res = w - ((w >> 1) & 0x55555555); |
res = (res & 0x33333333) + ((res >> 2) & 0x33333333); |
res = (res + (res >> 4)) & 0x0F0F0F0F; |
res = res + (res >> 8); |
return (res + (res >> 16)) & 0x000000FF; |
} |
/drivers/video/drm/radeon/radeon_display.c |
---|
835,17 → 835,13 |
struct drm_gem_object *obj) |
{ |
int ret; |
ENTER(); |
rfb->obj = obj; |
drm_helper_mode_fill_fb_struct(&rfb->base, mode_cmd); |
ret = drm_framebuffer_init(dev, &rfb->base, &radeon_fb_funcs); |
if (ret) { |
rfb->obj = NULL; |
return ret; |
} |
drm_helper_mode_fill_fb_struct(&rfb->base, mode_cmd); |
LEAVE(); |
return 0; |
} |
1043,8 → 1039,6 |
int i; |
int ret; |
ENTER(); |
drm_mode_config_init(rdev->ddev); |
rdev->mode_info.mode_config_initialized = true; |
1074,8 → 1068,6 |
/* init i2c buses */ |
radeon_i2c_init(rdev); |
dbgprintf("i2c init\n"); |
/* check combios for a valid hardcoded EDID - Sun servers */ |
if (!rdev->is_atom_bios) { |
/* check for hardcoded EDID in BIOS */ |
1087,8 → 1079,6 |
radeon_crtc_init(rdev->ddev, i); |
} |
dbgprintf("crtc init\n"); |
/* okay we should have all the bios connectors */ |
ret = radeon_setup_enc_conn(rdev->ddev); |
if (!ret) { |
1113,8 → 1103,6 |
radeon_fbdev_init(rdev); |
// drm_kms_helper_poll_init(rdev->ddev); |
LEAVE(); |
return 0; |
} |
1126,7 → 1114,7 |
// radeon_afmt_fini(rdev); |
// drm_kms_helper_poll_fini(rdev->ddev); |
// radeon_hpd_fini(rdev); |
drm_mode_config_cleanup(rdev->ddev); |
// drm_mode_config_cleanup(rdev->ddev); |
rdev->mode_info.mode_config_initialized = false; |
} |
/* free i2c buses */ |
1163,8 → 1151,6 |
radeon_crtc->h_border = 0; |
radeon_crtc->v_border = 0; |
ENTER(); |
list_for_each_entry(encoder, &dev->mode_config.encoder_list, head) { |
if (encoder->crtc != crtc) |
continue; |
1172,10 → 1158,6 |
connector = radeon_get_connector_for_encoder(encoder); |
radeon_connector = to_radeon_connector(connector); |
dbgprintf("native_hdisplay %d vdisplay %d\n", |
radeon_encoder->native_mode.hdisplay, |
radeon_encoder->native_mode.vdisplay); |
if (first) { |
/* set scaling */ |
if (radeon_encoder->rmx_type == RMX_OFF) |
1241,9 → 1223,6 |
radeon_crtc->vsc.full = dfixed_const(1); |
radeon_crtc->hsc.full = dfixed_const(1); |
} |
LEAVE(); |
return true; |
} |
/drivers/video/drm/radeon/radeon_family.h |
---|
91,6 → 91,8 |
CHIP_TAHITI, |
CHIP_PITCAIRN, |
CHIP_VERDE, |
CHIP_OLAND, |
CHIP_HAINAN, |
CHIP_LAST, |
}; |
/drivers/video/drm/radeon/radeon_fence.c |
---|
62,7 → 62,9 |
{ |
struct radeon_fence_driver *drv = &rdev->fence_drv[ring]; |
if (likely(rdev->wb.enabled || !drv->scratch_reg)) { |
if (drv->cpu_addr) { |
*drv->cpu_addr = cpu_to_le32(seq); |
} |
} else { |
WREG32(drv->scratch_reg, seq); |
} |
83,8 → 85,12 |
u32 seq = 0; |
if (likely(rdev->wb.enabled || !drv->scratch_reg)) { |
if (drv->cpu_addr) { |
seq = le32_to_cpu(*drv->cpu_addr); |
} else { |
seq = lower_32_bits(atomic64_read(&drv->last_seq)); |
} |
} else { |
seq = RREG32(drv->scratch_reg); |
} |
return seq; |
767,8 → 773,20 |
radeon_scratch_free(rdev, rdev->fence_drv[ring].scratch_reg); |
if (rdev->wb.use_event || !radeon_ring_supports_scratch_reg(rdev, &rdev->ring[ring])) { |
rdev->fence_drv[ring].scratch_reg = 0; |
if (ring != R600_RING_TYPE_UVD_INDEX) { |
index = R600_WB_EVENT_OFFSET + ring * 4; |
rdev->fence_drv[ring].cpu_addr = &rdev->wb.wb[index/4]; |
rdev->fence_drv[ring].gpu_addr = rdev->wb.gpu_addr + |
index; |
} else { |
/* put fence directly behind firmware */ |
index = ALIGN(rdev->uvd_fw->size, 8); |
rdev->fence_drv[ring].cpu_addr = rdev->uvd.cpu_addr + index; |
rdev->fence_drv[ring].gpu_addr = rdev->uvd.gpu_addr + index; |
} |
} else { |
r = radeon_scratch_get(rdev, &rdev->fence_drv[ring].scratch_reg); |
if (r) { |
dev_err(rdev->dev, "fence failed to get scratch register\n"); |
777,9 → 795,9 |
index = RADEON_WB_SCRATCH_OFFSET + |
rdev->fence_drv[ring].scratch_reg - |
rdev->scratch.reg_base; |
} |
rdev->fence_drv[ring].cpu_addr = &rdev->wb.wb[index/4]; |
rdev->fence_drv[ring].gpu_addr = rdev->wb.gpu_addr + index; |
} |
radeon_fence_write(rdev, atomic64_read(&rdev->fence_drv[ring].last_seq), ring); |
rdev->fence_drv[ring].initialized = true; |
dev_info(rdev->dev, "fence driver on ring %d use gpu addr 0x%016llx and cpu addr 0x%p\n", |
/drivers/video/drm/radeon/radeon_gart.c |
---|
249,8 → 249,6 |
p = t / (PAGE_SIZE / RADEON_GPU_PAGE_SIZE); |
for (i = 0; i < pages; i++, p++) { |
if (rdev->gart.pages[p]) { |
// pci_unmap_page(rdev->pdev, rdev->gart.pages_addr[p], |
// PAGE_SIZE, PCI_DMA_BIDIRECTIONAL); |
rdev->gart.pages[p] = NULL; |
rdev->gart.pages_addr[p] = rdev->dummy_page.addr; |
page_base = rdev->gart.pages_addr[p]; |
940,6 → 938,7 |
*/ |
static int radeon_vm_update_pdes(struct radeon_device *rdev, |
struct radeon_vm *vm, |
struct radeon_ib *ib, |
uint64_t start, uint64_t end) |
{ |
static const uint32_t incr = RADEON_VM_PTE_COUNT * 8; |
982,7 → 981,7 |
((last_pt + incr * count) != pt)) { |
if (count) { |
radeon_asic_vm_set_page(rdev, last_pde, |
radeon_asic_vm_set_page(rdev, ib, last_pde, |
last_pt, count, incr, |
RADEON_VM_PAGE_VALID); |
} |
996,7 → 995,7 |
} |
if (count) { |
radeon_asic_vm_set_page(rdev, last_pde, last_pt, count, |
radeon_asic_vm_set_page(rdev, ib, last_pde, last_pt, count, |
incr, RADEON_VM_PAGE_VALID); |
} |
1020,6 → 1019,7 |
*/ |
static void radeon_vm_update_ptes(struct radeon_device *rdev, |
struct radeon_vm *vm, |
struct radeon_ib *ib, |
uint64_t start, uint64_t end, |
uint64_t dst, uint32_t flags) |
{ |
1049,7 → 1049,7 |
if ((last_pte + 8 * count) != pte) { |
if (count) { |
radeon_asic_vm_set_page(rdev, last_pte, |
radeon_asic_vm_set_page(rdev, ib, last_pte, |
last_dst, count, |
RADEON_GPU_PAGE_SIZE, |
flags); |
1067,7 → 1067,8 |
} |
if (count) { |
radeon_asic_vm_set_page(rdev, last_pte, last_dst, count, |
radeon_asic_vm_set_page(rdev, ib, last_pte, |
last_dst, count, |
RADEON_GPU_PAGE_SIZE, flags); |
} |
} |
1091,8 → 1092,7 |
struct ttm_mem_reg *mem) |
{ |
unsigned ridx = rdev->asic->vm.pt_ring_index; |
struct radeon_ring *ring = &rdev->ring[ridx]; |
struct radeon_semaphore *sem = NULL; |
struct radeon_ib ib; |
struct radeon_bo_va *bo_va; |
unsigned nptes, npdes, ndw; |
uint64_t addr; |
1135,25 → 1135,13 |
bo_va->valid = false; |
} |
if (vm->fence && radeon_fence_signaled(vm->fence)) { |
radeon_fence_unref(&vm->fence); |
} |
if (vm->fence && vm->fence->ring != ridx) { |
r = radeon_semaphore_create(rdev, &sem); |
if (r) { |
return r; |
} |
} |
nptes = radeon_bo_ngpu_pages(bo); |
/* assume two extra pdes in case the mapping overlaps the borders */ |
npdes = (nptes >> RADEON_VM_BLOCK_SIZE) + 2; |
/* estimate number of dw needed */ |
/* semaphore, fence and padding */ |
ndw = 32; |
/* padding, etc. */ |
ndw = 64; |
if (RADEON_VM_BLOCK_SIZE > 11) |
/* reserve space for one header for every 2k dwords */ |
1172,33 → 1160,31 |
/* reserve space for pde addresses */ |
ndw += npdes * 2; |
r = radeon_ring_lock(rdev, ring, ndw); |
if (r) { |
return r; |
} |
/* update too big for an IB */ |
if (ndw > 0xfffff) |
return -ENOMEM; |
if (sem && radeon_fence_need_sync(vm->fence, ridx)) { |
radeon_semaphore_sync_rings(rdev, sem, vm->fence->ring, ridx); |
radeon_fence_note_sync(vm->fence, ridx); |
} |
r = radeon_ib_get(rdev, ridx, &ib, NULL, ndw * 4); |
ib.length_dw = 0; |
r = radeon_vm_update_pdes(rdev, vm, bo_va->soffset, bo_va->eoffset); |
r = radeon_vm_update_pdes(rdev, vm, &ib, bo_va->soffset, bo_va->eoffset); |
if (r) { |
radeon_ring_unlock_undo(rdev, ring); |
radeon_ib_free(rdev, &ib); |
return r; |
} |
radeon_vm_update_ptes(rdev, vm, bo_va->soffset, bo_va->eoffset, |
radeon_vm_update_ptes(rdev, vm, &ib, bo_va->soffset, bo_va->eoffset, |
addr, bo_va->flags); |
radeon_fence_unref(&vm->fence); |
r = radeon_fence_emit(rdev, &vm->fence, ridx); |
radeon_ib_sync_to(&ib, vm->fence); |
r = radeon_ib_schedule(rdev, &ib, NULL); |
if (r) { |
radeon_ring_unlock_undo(rdev, ring); |
radeon_ib_free(rdev, &ib); |
return r; |
} |
radeon_ring_unlock_commit(rdev, ring); |
radeon_semaphore_free(rdev, &sem, vm->fence); |
radeon_fence_unref(&vm->fence); |
vm->fence = radeon_fence_ref(ib.fence); |
radeon_ib_free(rdev, &ib); |
radeon_fence_unref(&vm->last_flush); |
return 0; |
1220,11 → 1206,13 |
int radeon_vm_bo_rmv(struct radeon_device *rdev, |
struct radeon_bo_va *bo_va) |
{ |
int r; |
int r = 0; |
mutex_lock(&rdev->vm_manager.lock); |
mutex_lock(&bo_va->vm->mutex); |
if (bo_va->soffset) { |
r = radeon_vm_bo_update_pte(rdev, bo_va->vm, bo_va->bo, NULL); |
} |
mutex_unlock(&rdev->vm_manager.lock); |
list_del(&bo_va->vm_list); |
mutex_unlock(&bo_va->vm->mutex); |
/drivers/video/drm/radeon/radeon_irq_kms.c |
---|
34,14 → 34,7 |
#define RADEON_WAIT_IDLE_TIMEOUT 200 |
#define DRM_IRQ_ARGS void *arg |
struct drm_driver { |
irqreturn_t(*irq_handler) (DRM_IRQ_ARGS); |
void (*irq_preinstall) (struct drm_device *dev); |
int (*irq_postinstall) (struct drm_device *dev); |
}; |
extern int irq_override; |
172,7 → 165,7 |
} |
/** |
* radeon_irq_kms_fini - tear down driver interrrupt info |
* radeon_irq_kms_fini - tear down driver interrupt info |
* |
* @rdev: radeon device pointer |
* |
/drivers/video/drm/radeon/radeon_legacy_crtc.c |
---|
426,7 → 426,8 |
if (unlikely(r != 0)) |
return r; |
/* Only 27 bit offset for legacy CRTC */ |
r = radeon_bo_pin(rbo, RADEON_GEM_DOMAIN_VRAM, &base); |
r = radeon_bo_pin_restricted(rbo, RADEON_GEM_DOMAIN_VRAM, 1 << 27, |
&base); |
if (unlikely(r != 0)) { |
radeon_bo_unreserve(rbo); |
return -EINVAL; |
1030,11 → 1031,9 |
static void radeon_crtc_prepare(struct drm_crtc *crtc) |
{ |
struct radeon_crtc *radeon_crtc = to_radeon_crtc(crtc); |
struct drm_device *dev = crtc->dev; |
struct drm_crtc *crtci; |
radeon_crtc->in_mode_set = true; |
/* |
* The hardware wedges sometimes if you reconfigure one CRTC |
* whilst another is running (see fdo bug #24611). |
1045,7 → 1044,6 |
static void radeon_crtc_commit(struct drm_crtc *crtc) |
{ |
struct radeon_crtc *radeon_crtc = to_radeon_crtc(crtc); |
struct drm_device *dev = crtc->dev; |
struct drm_crtc *crtci; |
1056,7 → 1054,6 |
if (crtci->enabled) |
radeon_crtc_dpms(crtci, DRM_MODE_DPMS_ON); |
} |
radeon_crtc->in_mode_set = false; |
} |
static const struct drm_crtc_helper_funcs legacy_helper_funcs = { |
/drivers/video/drm/radeon/radeon_legacy_encoders.c |
---|
640,6 → 640,14 |
enum drm_connector_status found = connector_status_disconnected; |
bool color = true; |
/* just don't bother on RN50 those chip are often connected to remoting |
* console hw and often we get failure to load detect those. So to make |
* everyone happy report the encoder as always connected. |
*/ |
if (ASIC_IS_RN50(rdev)) { |
return connector_status_connected; |
} |
/* save the regs we need */ |
vclk_ecp_cntl = RREG32_PLL(RADEON_VCLK_ECP_CNTL); |
crtc_ext_cntl = RREG32(RADEON_CRTC_EXT_CNTL); |
/drivers/video/drm/radeon/radeon_mode.h |
---|
302,7 → 302,6 |
u16 lut_r[256], lut_g[256], lut_b[256]; |
bool enabled; |
bool can_tile; |
bool in_mode_set; |
uint32_t crtc_offset; |
struct drm_gem_object *cursor_bo; |
uint64_t cursor_addr; |
490,6 → 489,29 |
#define ENCODER_MODE_IS_DP(em) (((em) == ATOM_ENCODER_MODE_DP) || \ |
((em) == ATOM_ENCODER_MODE_DP_MST)) |
struct atom_clock_dividers { |
u32 post_div; |
union { |
struct { |
#ifdef __BIG_ENDIAN |
u32 reserved : 6; |
u32 whole_fb_div : 12; |
u32 frac_fb_div : 14; |
#else |
u32 frac_fb_div : 14; |
u32 whole_fb_div : 12; |
u32 reserved : 6; |
#endif |
}; |
u32 fb_div; |
}; |
u32 ref_div; |
bool enable_post_div; |
bool enable_dithen; |
u32 vco_mode; |
u32 real_clock; |
}; |
extern enum radeon_tv_std |
radeon_combios_get_tv_info(struct radeon_device *rdev); |
extern enum radeon_tv_std |
/drivers/video/drm/radeon/radeon_object.h |
---|
58,7 → 58,7 |
static inline void radeon_bo_unreserve(struct radeon_bo *bo) |
{ |
ttm_bo_unreserve(&bo->tbo); |
// ttm_bo_unreserve(&bo->tbo); |
} |
/** |
82,7 → 82,11 |
static inline bool radeon_bo_is_reserved(struct radeon_bo *bo) |
{ |
#ifdef __TTM__ |
return ttm_bo_is_reserved(&bo->tbo); |
#else |
return !!atomic_read(&bo->tbo.reserved); |
#endif |
} |
static inline unsigned radeon_bo_ngpu_pages(struct radeon_bo *bo) |
130,7 → 134,7 |
extern void radeon_bo_fini(struct radeon_device *rdev); |
extern void radeon_bo_list_add_object(struct radeon_bo_list *lobj, |
struct list_head *head); |
extern int radeon_bo_list_validate(struct list_head *head); |
extern int radeon_bo_list_validate(struct list_head *head, int ring); |
extern int radeon_bo_fbdev_mmap(struct radeon_bo *bo, |
struct vm_area_struct *vma); |
extern int radeon_bo_set_tiling_flags(struct radeon_bo *bo, |
/drivers/video/drm/radeon/radeon_object_kos.c |
---|
9,25 → 9,6 |
static struct drm_mm mm_vram; |
/** |
* Initialize an already allocate GEM object of the specified size with |
* shmfs backing store. |
*/ |
int drm_gem_object_init(struct drm_device *dev, |
struct drm_gem_object *obj, size_t size) |
{ |
BUG_ON((size & (PAGE_SIZE - 1)) != 0); |
obj->dev = dev; |
obj->filp = NULL; |
atomic_set(&obj->handle_count, 0); |
obj->size = size; |
return 0; |
} |
int drm_mm_alloc(struct drm_mm *mm, size_t num_pages, |
struct drm_mm_node **node) |
{ |
215,10 → 196,10 |
{ |
u32_t *pagelist; |
bo->kptr = KernelAlloc( bo->tbo.num_pages << PAGE_SHIFT ); |
dbgprintf("kernel alloc %x\n", bo->kptr ); |
// dbgprintf("kernel alloc %x\n", bo->kptr ); |
pagelist = &((u32_t*)page_tabs)[(u32_t)bo->kptr >> 12]; |
dbgprintf("pagelist %x\n", pagelist); |
// dbgprintf("pagelist %x\n", pagelist); |
radeon_gart_bind(bo->rdev, bo->tbo.offset, |
bo->tbo.vm_node->size, pagelist, NULL); |
bo->tbo.offset += (u64)bo->rdev->mc.gtt_start; |
245,6 → 226,67 |
return r; |
}; |
int radeon_bo_pin_restricted(struct radeon_bo *bo, u32 domain, u64 max_offset, |
u64 *gpu_addr) |
{ |
int r, i; |
if (bo->pin_count) { |
bo->pin_count++; |
if (gpu_addr) |
*gpu_addr = radeon_bo_gpu_offset(bo); |
if (max_offset != 0) { |
u64 domain_start; |
if (domain == RADEON_GEM_DOMAIN_VRAM) |
domain_start = bo->rdev->mc.vram_start; |
else |
domain_start = bo->rdev->mc.gtt_start; |
WARN_ON_ONCE(max_offset < |
(radeon_bo_gpu_offset(bo) - domain_start)); |
} |
return 0; |
} |
// radeon_ttm_placement_from_domain(bo, domain); |
if (domain == RADEON_GEM_DOMAIN_VRAM) { |
/* force to pin into visible video ram */ |
// bo->placement.lpfn = bo->rdev->mc.visible_vram_size >> PAGE_SHIFT; |
bo->tbo.offset += (u64)bo->rdev->mc.vram_start; |
} |
else if (bo->domain & RADEON_GEM_DOMAIN_GTT) |
{ |
u32_t *pagelist; |
bo->kptr = KernelAlloc( bo->tbo.num_pages << PAGE_SHIFT ); |
dbgprintf("kernel alloc %x\n", bo->kptr ); |
pagelist = &((u32_t*)page_tabs)[(u32_t)bo->kptr >> 12]; |
dbgprintf("pagelist %x\n", pagelist); |
radeon_gart_bind(bo->rdev, bo->tbo.offset, |
bo->tbo.vm_node->size, pagelist, NULL); |
bo->tbo.offset += (u64)bo->rdev->mc.gtt_start; |
} |
else |
{ |
DRM_ERROR("Unknown placement %x\n", bo->domain); |
bo->tbo.offset = -1; |
r = -1; |
}; |
if (likely(r == 0)) { |
bo->pin_count = 1; |
if (gpu_addr != NULL) |
*gpu_addr = radeon_bo_gpu_offset(bo); |
} |
if (unlikely(r != 0)) |
dev_err(bo->rdev->dev, "%p pin failed\n", bo); |
return r; |
} |
int radeon_bo_unpin(struct radeon_bo *bo) |
{ |
int r = 0; |
375,24 → 417,7 |
} |
/** |
* Allocate a GEM object of the specified size with shmfs backing store |
*/ |
struct drm_gem_object * |
drm_gem_object_alloc(struct drm_device *dev, size_t size) |
{ |
struct drm_gem_object *obj; |
BUG_ON((size & (PAGE_SIZE - 1)) != 0); |
obj = kzalloc(sizeof(*obj), GFP_KERNEL); |
obj->dev = dev; |
obj->size = size; |
return obj; |
} |
int radeon_fb_bo_create(struct radeon_device *rdev, struct drm_gem_object *gobj, |
unsigned long size, bool kernel, u32 domain, |
struct radeon_bo **bo_ptr) |
/drivers/video/drm/radeon/radeon_pm.c |
---|
163,7 → 163,7 |
/* starting with BTC, there is one state that is used for both |
* MH and SH. Difference is that we always use the high clock index for |
* mclk. |
* mclk and vddci. |
*/ |
if ((rdev->pm.pm_method == PM_METHOD_PROFILE) && |
(rdev->family >= CHIP_BARTS) && |
228,7 → 228,7 |
static void radeon_pm_set_clocks(struct radeon_device *rdev) |
{ |
int i; |
int i, r; |
/* no need to take locks, etc. if nothing's going to change */ |
if ((rdev->pm.requested_clock_mode_index == rdev->pm.current_clock_mode_index) && |
242,9 → 242,18 |
/* wait for the rings to drain */ |
for (i = 0; i < RADEON_NUM_RINGS; i++) { |
struct radeon_ring *ring = &rdev->ring[i]; |
if (ring->ready) |
radeon_fence_wait_empty_locked(rdev, i); |
if (!ring->ready) { |
continue; |
} |
r = radeon_fence_wait_empty_locked(rdev, i); |
if (r) { |
/* needs a GPU reset dont reset here */ |
mutex_unlock(&rdev->ring_lock); |
// up_write(&rdev->pm.mclk_lock); |
mutex_unlock(&rdev->ddev->struct_mutex); |
return; |
} |
} |
radeon_unmap_vram_bos(rdev); |
485,6 → 494,7 |
rdev->pm.current_sclk = rdev->pm.default_sclk; |
rdev->pm.current_mclk = rdev->pm.default_mclk; |
rdev->pm.current_vddc = rdev->pm.power_state[rdev->pm.default_power_state_index].clock_info[0].voltage.voltage; |
rdev->pm.current_vddci = rdev->pm.power_state[rdev->pm.default_power_state_index].clock_info[0].voltage.vddci; |
if (rdev->pm.pm_method == PM_METHOD_DYNPM |
&& rdev->pm.dynpm_state == DYNPM_STATE_SUSPENDED) { |
rdev->pm.dynpm_state = DYNPM_STATE_ACTIVE; |
672,13 → 682,17 |
struct radeon_device *rdev = dev->dev_private; |
seq_printf(m, "default engine clock: %u0 kHz\n", rdev->pm.default_sclk); |
/* radeon_get_engine_clock is not reliable on APUs so just print the current clock */ |
if ((rdev->family >= CHIP_PALM) && (rdev->flags & RADEON_IS_IGP)) |
seq_printf(m, "current engine clock: %u0 kHz\n", rdev->pm.current_sclk); |
else |
seq_printf(m, "current engine clock: %u0 kHz\n", radeon_get_engine_clock(rdev)); |
seq_printf(m, "default memory clock: %u0 kHz\n", rdev->pm.default_mclk); |
if (rdev->asic->get_memory_clock) |
if (rdev->asic->pm.get_memory_clock) |
seq_printf(m, "current memory clock: %u0 kHz\n", radeon_get_memory_clock(rdev)); |
if (rdev->pm.current_vddc) |
seq_printf(m, "voltage: %u mV\n", rdev->pm.current_vddc); |
if (rdev->asic->get_pcie_lanes) |
if (rdev->asic->pm.get_pcie_lanes) |
seq_printf(m, "PCIE lanes: %d\n", radeon_get_pcie_lanes(rdev)); |
return 0; |
/drivers/video/drm/radeon/radeon_reg.h |
---|
3706,4 → 3706,19 |
#define RV530_GB_PIPE_SELECT2 0x4124 |
#define RADEON_CP_PACKET_GET_TYPE(h) (((h) >> 30) & 3) |
#define RADEON_CP_PACKET_GET_COUNT(h) (((h) >> 16) & 0x3FFF) |
#define RADEON_CP_PACKET0_GET_ONE_REG_WR(h) (((h) >> 15) & 1) |
#define RADEON_CP_PACKET3_GET_OPCODE(h) (((h) >> 8) & 0xFF) |
#define R100_CP_PACKET0_GET_REG(h) (((h) & 0x1FFF) << 2) |
#define R600_CP_PACKET0_GET_REG(h) (((h) & 0xFFFF) << 2) |
#define RADEON_PACKET_TYPE0 0 |
#define RADEON_PACKET_TYPE1 1 |
#define RADEON_PACKET_TYPE2 2 |
#define RADEON_PACKET_TYPE3 3 |
#define RADEON_PACKET3_NOP 0x10 |
#define RADEON_VLINE_STAT (1 << 12) |
#endif |
/drivers/video/drm/radeon/radeon_ring.c |
---|
109,6 → 109,25 |
} |
/** |
* radeon_ib_sync_to - sync to fence before executing the IB |
* |
* @ib: IB object to add fence to |
* @fence: fence to sync to |
* |
* Sync to the fence before executing the IB |
*/ |
void radeon_ib_sync_to(struct radeon_ib *ib, struct radeon_fence *fence) |
{ |
struct radeon_fence *other; |
if (!fence) |
return; |
other = ib->sync_to[fence->ring]; |
ib->sync_to[fence->ring] = radeon_fence_later(fence, other); |
} |
/** |
* radeon_ib_schedule - schedule an IB (Indirect Buffer) on the ring |
* |
* @rdev: radeon_device pointer |
161,7 → 180,8 |
radeon_semaphore_free(rdev, &ib->semaphore, NULL); |
} |
/* if we can't remember our last VM flush then flush now! */ |
if (ib->vm && !ib->vm->last_flush) { |
/* XXX figure out why we have to flush for every IB */ |
if (ib->vm /*&& !ib->vm->last_flush*/) { |
radeon_ring_vm_flush(rdev, ib->ring, ib->vm); |
} |
if (const_ib) { |
349,7 → 369,7 |
{ |
u32 rptr; |
if (rdev->wb.enabled) |
if (rdev->wb.enabled && ring != &rdev->ring[R600_RING_TYPE_UVD_INDEX]) |
rptr = le32_to_cpu(rdev->wb.wb[ring->rptr_offs/4]); |
else |
rptr = RREG32(ring->rptr_reg); |
377,8 → 397,18 |
{ |
int r; |
/* make sure we aren't trying to allocate more space than there is on the ring */ |
if (ndw > (ring->ring_size / 4)) |
return -ENOMEM; |
/* Align requested size with padding so unlock_commit can |
* pad safely */ |
radeon_ring_free_size(rdev, ring); |
if (ring->ring_free_dw == (ring->ring_size / 4)) { |
/* This is an empty ring update lockup info to avoid |
* false positive. |
*/ |
radeon_ring_lockup_update(ring); |
} |
ndw = (ndw + ring->align_mask) & ~ring->align_mask; |
while (ndw > (ring->ring_free_dw - 1)) { |
radeon_ring_free_size(rdev, ring); |
799,18 → 829,20 |
return 0; |
} |
static int radeon_ring_type_gfx_index = RADEON_RING_TYPE_GFX_INDEX; |
static int cayman_ring_type_cp1_index = CAYMAN_RING_TYPE_CP1_INDEX; |
static int cayman_ring_type_cp2_index = CAYMAN_RING_TYPE_CP2_INDEX; |
static int radeon_ring_type_dma1_index = R600_RING_TYPE_DMA_INDEX; |
static int radeon_ring_type_dma2_index = CAYMAN_RING_TYPE_DMA1_INDEX; |
static int radeon_gfx_index = RADEON_RING_TYPE_GFX_INDEX; |
static int cayman_cp1_index = CAYMAN_RING_TYPE_CP1_INDEX; |
static int cayman_cp2_index = CAYMAN_RING_TYPE_CP2_INDEX; |
static int radeon_dma1_index = R600_RING_TYPE_DMA_INDEX; |
static int radeon_dma2_index = CAYMAN_RING_TYPE_DMA1_INDEX; |
static int r600_uvd_index = R600_RING_TYPE_UVD_INDEX; |
static struct drm_info_list radeon_debugfs_ring_info_list[] = { |
{"radeon_ring_gfx", radeon_debugfs_ring_info, 0, &radeon_ring_type_gfx_index}, |
{"radeon_ring_cp1", radeon_debugfs_ring_info, 0, &cayman_ring_type_cp1_index}, |
{"radeon_ring_cp2", radeon_debugfs_ring_info, 0, &cayman_ring_type_cp2_index}, |
{"radeon_ring_dma1", radeon_debugfs_ring_info, 0, &radeon_ring_type_dma1_index}, |
{"radeon_ring_dma2", radeon_debugfs_ring_info, 0, &radeon_ring_type_dma2_index}, |
{"radeon_ring_gfx", radeon_debugfs_ring_info, 0, &radeon_gfx_index}, |
{"radeon_ring_cp1", radeon_debugfs_ring_info, 0, &cayman_cp1_index}, |
{"radeon_ring_cp2", radeon_debugfs_ring_info, 0, &cayman_cp2_index}, |
{"radeon_ring_dma1", radeon_debugfs_ring_info, 0, &radeon_dma1_index}, |
{"radeon_ring_dma2", radeon_debugfs_ring_info, 0, &radeon_dma2_index}, |
{"radeon_ring_uvd", radeon_debugfs_ring_info, 0, &r600_uvd_index}, |
}; |
static int radeon_debugfs_sa_info(struct seq_file *m, void *data) |
/drivers/video/drm/radeon/radeon_semaphore.c |
---|
95,6 → 95,10 |
/* we assume caller has already allocated space on waiters ring */ |
radeon_semaphore_emit_wait(rdev, waiter, semaphore); |
/* for debugging lockup only, used by sysfs debug files */ |
rdev->ring[signaler].last_semaphore_signal_addr = semaphore->gpu_addr; |
rdev->ring[waiter].last_semaphore_wait_addr = semaphore->gpu_addr; |
return 0; |
} |
/drivers/video/drm/radeon/radeon_ttm.c |
---|
74,6 → 74,8 |
struct drm_global_reference *global_ref; |
int r; |
ENTER(); |
rdev->mman.mem_global_referenced = false; |
global_ref = &rdev->mman.mem_global_ref; |
global_ref->global_type = DRM_GLOBAL_TTM_MEM; |
102,10 → 104,14 |
} |
rdev->mman.mem_global_referenced = true; |
LEAVE(); |
return 0; |
} |
static int radeon_invalidate_caches(struct ttm_bo_device *bdev, uint32_t flags) |
{ |
return 0; |
116,6 → 122,8 |
{ |
struct radeon_device *rdev; |
ENTER(); |
rdev = radeon_get_rdev(bdev); |
switch (type) { |
159,11 → 167,170 |
DRM_ERROR("Unsupported memory type %u\n", (unsigned)type); |
return -EINVAL; |
} |
LEAVE(); |
return 0; |
} |
static void radeon_evict_flags(struct ttm_buffer_object *bo, |
struct ttm_placement *placement) |
{ |
struct radeon_bo *rbo; |
static u32 placements = TTM_PL_MASK_CACHING | TTM_PL_FLAG_SYSTEM; |
if (!radeon_ttm_bo_is_radeon_bo(bo)) { |
placement->fpfn = 0; |
placement->lpfn = 0; |
placement->placement = &placements; |
placement->busy_placement = &placements; |
placement->num_placement = 1; |
placement->num_busy_placement = 1; |
return; |
} |
rbo = container_of(bo, struct radeon_bo, tbo); |
switch (bo->mem.mem_type) { |
case TTM_PL_VRAM: |
if (rbo->rdev->ring[RADEON_RING_TYPE_GFX_INDEX].ready == false) |
radeon_ttm_placement_from_domain(rbo, RADEON_GEM_DOMAIN_CPU); |
else |
radeon_ttm_placement_from_domain(rbo, RADEON_GEM_DOMAIN_GTT); |
break; |
case TTM_PL_TT: |
default: |
radeon_ttm_placement_from_domain(rbo, RADEON_GEM_DOMAIN_CPU); |
} |
*placement = rbo->placement; |
} |
static int radeon_verify_access(struct ttm_buffer_object *bo, struct file *filp) |
{ |
return 0; |
} |
static void radeon_move_null(struct ttm_buffer_object *bo, |
struct ttm_mem_reg *new_mem) |
{ |
struct ttm_mem_reg *old_mem = &bo->mem; |
BUG_ON(old_mem->mm_node != NULL); |
*old_mem = *new_mem; |
new_mem->mm_node = NULL; |
} |
static void radeon_ttm_io_mem_free(struct ttm_bo_device *bdev, struct ttm_mem_reg *mem) |
{ |
} |
static int radeon_sync_obj_wait(void *sync_obj, bool lazy, bool interruptible) |
{ |
return radeon_fence_wait((struct radeon_fence *)sync_obj, interruptible); |
} |
static int radeon_sync_obj_flush(void *sync_obj) |
{ |
return 0; |
} |
static void radeon_sync_obj_unref(void **sync_obj) |
{ |
radeon_fence_unref((struct radeon_fence **)sync_obj); |
} |
static void *radeon_sync_obj_ref(void *sync_obj) |
{ |
return radeon_fence_ref((struct radeon_fence *)sync_obj); |
} |
static bool radeon_sync_obj_signaled(void *sync_obj) |
{ |
return radeon_fence_signaled((struct radeon_fence *)sync_obj); |
} |
/* |
* TTM backend functions. |
*/ |
struct radeon_ttm_tt { |
struct ttm_dma_tt ttm; |
struct radeon_device *rdev; |
u64 offset; |
}; |
static int radeon_ttm_backend_bind(struct ttm_tt *ttm, |
struct ttm_mem_reg *bo_mem) |
{ |
struct radeon_ttm_tt *gtt = (void*)ttm; |
int r; |
gtt->offset = (unsigned long)(bo_mem->start << PAGE_SHIFT); |
if (!ttm->num_pages) { |
WARN(1, "nothing to bind %lu pages for mreg %p back %p!\n", |
ttm->num_pages, bo_mem, ttm); |
} |
r = radeon_gart_bind(gtt->rdev, gtt->offset, |
ttm->num_pages, ttm->pages, gtt->ttm.dma_address); |
if (r) { |
DRM_ERROR("failed to bind %lu pages at 0x%08X\n", |
ttm->num_pages, (unsigned)gtt->offset); |
return r; |
} |
return 0; |
} |
static int radeon_ttm_backend_unbind(struct ttm_tt *ttm) |
{ |
struct radeon_ttm_tt *gtt = (void *)ttm; |
radeon_gart_unbind(gtt->rdev, gtt->offset, ttm->num_pages); |
return 0; |
} |
static void radeon_ttm_backend_destroy(struct ttm_tt *ttm) |
{ |
struct radeon_ttm_tt *gtt = (void *)ttm; |
ttm_dma_tt_fini(>t->ttm); |
kfree(gtt); |
} |
static struct ttm_backend_func radeon_backend_func = { |
.bind = &radeon_ttm_backend_bind, |
.unbind = &radeon_ttm_backend_unbind, |
.destroy = &radeon_ttm_backend_destroy, |
}; |
static struct ttm_tt *radeon_ttm_tt_create(struct ttm_bo_device *bdev, |
unsigned long size, uint32_t page_flags, |
struct page *dummy_read_page) |
{ |
struct radeon_device *rdev; |
struct radeon_ttm_tt *gtt; |
rdev = radeon_get_rdev(bdev); |
#if __OS_HAS_AGP |
if (rdev->flags & RADEON_IS_AGP) { |
return ttm_agp_tt_create(bdev, rdev->ddev->agp->bridge, |
size, page_flags, dummy_read_page); |
} |
#endif |
gtt = kzalloc(sizeof(struct radeon_ttm_tt), GFP_KERNEL); |
if (gtt == NULL) { |
return NULL; |
} |
gtt->ttm.ttm.func = &radeon_backend_func; |
gtt->rdev = rdev; |
if (ttm_dma_tt_init(>t->ttm, bdev, size, page_flags, dummy_read_page)) { |
kfree(gtt); |
return NULL; |
} |
return >t->ttm.ttm; |
} |
static struct ttm_bo_driver radeon_bo_driver = { |
// .create_ttm_backend_entry = &radeon_create_ttm_backend_entry, |
.ttm_tt_create = &radeon_ttm_tt_create, |
// .ttm_tt_populate = &radeon_ttm_tt_populate, |
// .ttm_tt_unpopulate = &radeon_ttm_tt_unpopulate, |
// .invalidate_caches = &radeon_invalidate_caches, |
.init_mem_type = &radeon_init_mem_type, |
// .evict_flags = &radeon_evict_flags, |
176,6 → 343,8 |
// .sync_obj_ref = &radeon_sync_obj_ref, |
// .move_notify = &radeon_bo_move_notify, |
// .fault_reserve_notify = &radeon_bo_fault_reserve_notify, |
// .io_mem_reserve = &radeon_ttm_io_mem_reserve, |
// .io_mem_free = &radeon_ttm_io_mem_free, |
}; |
int radeon_ttm_init(struct radeon_device *rdev) |
182,6 → 351,8 |
{ |
int r; |
ENTER(); |
r = radeon_ttm_global_init(rdev); |
if (r) { |
return r; |
202,21 → 373,23 |
DRM_ERROR("Failed initializing VRAM heap.\n"); |
return r; |
} |
r = radeon_bo_create(rdev, NULL, 256 * 1024, true, |
RADEON_GEM_DOMAIN_VRAM, |
&rdev->stollen_vga_memory); |
if (r) { |
return r; |
} |
r = radeon_bo_reserve(rdev->stollen_vga_memory, false); |
if (r) |
return r; |
r = radeon_bo_pin(rdev->stollen_vga_memory, RADEON_GEM_DOMAIN_VRAM, NULL); |
radeon_bo_unreserve(rdev->stollen_vga_memory); |
if (r) { |
radeon_bo_unref(&rdev->stollen_vga_memory); |
return r; |
} |
// r = radeon_bo_create(rdev, 256 * 1024, PAGE_SIZE, true, |
// RADEON_GEM_DOMAIN_VRAM, |
// NULL, &rdev->stollen_vga_memory); |
// if (r) { |
// return r; |
// } |
// r = radeon_bo_reserve(rdev->stollen_vga_memory, false); |
// if (r) |
// return r; |
// r = radeon_bo_pin(rdev->stollen_vga_memory, RADEON_GEM_DOMAIN_VRAM, NULL); |
// radeon_bo_unreserve(rdev->stollen_vga_memory); |
// if (r) { |
// radeon_bo_unref(&rdev->stollen_vga_memory); |
// return r; |
// } |
DRM_INFO("radeon: %uM of VRAM memory ready\n", |
(unsigned)rdev->mc.real_vram_size / (1024 * 1024)); |
r = ttm_bo_init_mm(&rdev->mman.bdev, TTM_PL_TT, |
227,36 → 400,76 |
} |
DRM_INFO("radeon: %uM of GTT memory ready.\n", |
(unsigned)(rdev->mc.gtt_size / (1024 * 1024))); |
if (unlikely(rdev->mman.bdev.dev_mapping == NULL)) { |
rdev->mman.bdev.dev_mapping = rdev->ddev->dev_mapping; |
} |
r = radeon_ttm_debugfs_init(rdev); |
if (r) { |
DRM_ERROR("Failed to init debugfs\n"); |
return r; |
} |
LEAVE(); |
return 0; |
} |
static struct vm_operations_struct radeon_ttm_vm_ops; |
static const struct vm_operations_struct *ttm_vm_ops = NULL; |
/* this should only be called at bootup or when userspace |
* isn't running */ |
void radeon_ttm_set_active_vram_size(struct radeon_device *rdev, u64 size) |
{ |
struct ttm_mem_type_manager *man; |
if (!rdev->mman.initialized) |
return; |
man = &rdev->mman.bdev.man[TTM_PL_VRAM]; |
/* this just adjusts TTM size idea, which sets lpfn to the correct value */ |
man->size = size >> PAGE_SHIFT; |
} |
static struct vm_operations_struct radeon_ttm_vm_ops; |
static const struct vm_operations_struct *ttm_vm_ops = NULL; |
#if 0 |
radeon_bo_init |
{ |
<6>[drm] Detected VRAM RAM=1024M, BAR=256M |
<6>[drm] RAM width 128bits DDR |
radeon_ttm_init |
{ |
radeon_ttm_global_init |
{ |
radeon_ttm_mem_global_init |
ttm_bo_global_init |
} |
ttm_bo_device_init |
{ |
ttm_bo_init_mm |
{ |
radeon_init_mem_type |
}; |
} |
ttm_bo_init_mm |
{ |
radeon_init_mem_type |
ttm_bo_man_init |
} |
<6>[drm] radeon: 1024M of VRAM memory ready |
ttm_bo_init_mm |
{ |
radeon_init_mem_type |
ttm_bo_man_init |
} |
<6>[drm] radeon: 512M of GTT memory ready. |
} |
}; |
#endif |
/drivers/video/drm/radeon/rdisplay.c |
---|
257,7 → 257,7 |
}; |
safe_sti(ifl); |
init_bitmaps(); |
// init_bitmaps(); |
LEAVE(); |
/drivers/video/drm/radeon/rdisplay_kms.c |
---|
530,7 → 530,7 |
}; |
safe_sti(ifl); |
init_bitmaps(); |
// init_bitmaps(); |
LEAVE(); |
632,7 → 632,7 |
size = mode_cmd->pitches[0] * height; |
aligned_size = ALIGN(size, PAGE_SIZE); |
#ifndef __TTM__ |
ret = drm_gem_object_init(rdev->ddev, &kos_bo.gem_base, aligned_size); |
if (unlikely(ret)) { |
printk(KERN_ERR "failed to allocate framebuffer (%d)\n", |
639,11 → 639,12 |
aligned_size); |
return -ENOMEM; |
} |
#endif |
kos_bo.rdev = rdev; |
kos_bo.gem_base.driver_private = NULL; |
kos_bo.surface_reg = -1; |
kos_bo.domain = RADEON_GEM_DOMAIN_VRAM; |
// kos_bo.domain = RADEON_GEM_DOMAIN_VRAM; |
INIT_LIST_HEAD(&kos_bo.list); |
676,7 → 677,7 |
return 0; |
} |
#if 0 |
typedef struct |
{ |
int left; |
900,3 → 901,4 |
return ret; |
}; |
#endif |
/drivers/video/drm/radeon/reg_srcs/cayman |
---|
1,5 → 1,6 |
cayman 0x9400 |
0x0000802C GRBM_GFX_INDEX |
0x00008040 WAIT_UNTIL |
0x000084FC CP_STRMOUT_CNTL |
0x000085F0 CP_COHER_CNTL |
0x000085F4 CP_COHER_SIZE |
/drivers/video/drm/radeon/reg_srcs/rv515 |
---|
324,6 → 324,8 |
0x46AC US_OUT_FMT_2 |
0x46B0 US_OUT_FMT_3 |
0x46B4 US_W_FMT |
0x46C0 RB3D_COLOR_CLEAR_VALUE_AR |
0x46C4 RB3D_COLOR_CLEAR_VALUE_GB |
0x4BC0 FG_FOG_BLEND |
0x4BC4 FG_FOG_FACTOR |
0x4BC8 FG_FOG_COLOR_R |
/drivers/video/drm/radeon/rs400.c |
---|
417,6 → 417,12 |
} |
/* Enable IRQ */ |
if (!rdev->irq.installed) { |
r = radeon_irq_kms_init(rdev); |
if (r) |
return r; |
} |
r100_irq_set(rdev); |
rdev->config.r300.hdp_cntl = RREG32(RADEON_HOST_PATH_CNTL); |
/* 1M ring buffer */ |
483,9 → 489,6 |
r = radeon_fence_driver_init(rdev); |
if (r) |
return r; |
r = radeon_irq_kms_init(rdev); |
if (r) |
return r; |
/* Memory manager */ |
r = radeon_bo_init(rdev); |
if (r) |
/drivers/video/drm/radeon/rs600.c |
---|
52,19 → 52,60 |
AVIVO_D2CRTC_H_TOTAL - AVIVO_D1CRTC_H_TOTAL |
}; |
static bool avivo_is_in_vblank(struct radeon_device *rdev, int crtc) |
{ |
if (RREG32(AVIVO_D1CRTC_STATUS + crtc_offsets[crtc]) & AVIVO_D1CRTC_V_BLANK) |
return true; |
else |
return false; |
} |
static bool avivo_is_counter_moving(struct radeon_device *rdev, int crtc) |
{ |
u32 pos1, pos2; |
pos1 = RREG32(AVIVO_D1CRTC_STATUS_POSITION + crtc_offsets[crtc]); |
pos2 = RREG32(AVIVO_D1CRTC_STATUS_POSITION + crtc_offsets[crtc]); |
if (pos1 != pos2) |
return true; |
else |
return false; |
} |
/** |
* avivo_wait_for_vblank - vblank wait asic callback. |
* |
* @rdev: radeon_device pointer |
* @crtc: crtc to wait for vblank on |
* |
* Wait for vblank on the requested crtc (r5xx-r7xx). |
*/ |
void avivo_wait_for_vblank(struct radeon_device *rdev, int crtc) |
{ |
int i; |
unsigned i = 0; |
if (crtc >= rdev->num_crtc) |
return; |
if (RREG32(AVIVO_D1CRTC_CONTROL + crtc_offsets[crtc]) & AVIVO_CRTC_EN) { |
for (i = 0; i < rdev->usec_timeout; i++) { |
if (!(RREG32(AVIVO_D1CRTC_STATUS + crtc_offsets[crtc]) & AVIVO_D1CRTC_V_BLANK)) |
if (!(RREG32(AVIVO_D1CRTC_CONTROL + crtc_offsets[crtc]) & AVIVO_CRTC_EN)) |
return; |
/* depending on when we hit vblank, we may be close to active; if so, |
* wait for another frame. |
*/ |
while (avivo_is_in_vblank(rdev, crtc)) { |
if (i++ % 100 == 0) { |
if (!avivo_is_counter_moving(rdev, crtc)) |
break; |
udelay(1); |
} |
} |
while (!avivo_is_in_vblank(rdev, crtc)) { |
if (i++ % 100 == 0) { |
if (!avivo_is_counter_moving(rdev, crtc)) |
break; |
} |
for (i = 0; i < rdev->usec_timeout; i++) { |
if (RREG32(AVIVO_D1CRTC_STATUS + crtc_offsets[crtc]) & AVIVO_D1CRTC_V_BLANK) |
break; |
712,6 → 753,12 |
} |
/* Enable IRQ */ |
if (!rdev->irq.installed) { |
r = radeon_irq_kms_init(rdev); |
if (r) |
return r; |
} |
rs600_irq_set(rdev); |
rdev->config.r300.hdp_cntl = RREG32(RADEON_HOST_PATH_CNTL); |
/* 1M ring buffer */ |
778,9 → 825,6 |
r = radeon_fence_driver_init(rdev); |
if (r) |
return r; |
r = radeon_irq_kms_init(rdev); |
if (r) |
return r; |
/* Memory manager */ |
r = radeon_bo_init(rdev); |
if (r) |
/drivers/video/drm/radeon/rs690.c |
---|
148,6 → 148,8 |
static void rs690_mc_init(struct radeon_device *rdev) |
{ |
u64 base; |
uint32_t h_addr, l_addr; |
unsigned long long k8_addr; |
rs400_gart_adjust_size(rdev); |
rdev->mc.vram_is_ddr = true; |
160,6 → 162,27 |
base = RREG32_MC(R_000100_MCCFG_FB_LOCATION); |
base = G_000100_MC_FB_START(base) << 16; |
rdev->mc.igp_sideport_enabled = radeon_atombios_sideport_present(rdev); |
/* Use K8 direct mapping for fast fb access. */ |
rdev->fastfb_working = false; |
h_addr = G_00005F_K8_ADDR_EXT(RREG32_MC(R_00005F_MC_MISC_UMA_CNTL)); |
l_addr = RREG32_MC(R_00001E_K8_FB_LOCATION); |
k8_addr = ((unsigned long long)h_addr) << 32 | l_addr; |
#if defined(CONFIG_X86_32) && !defined(CONFIG_X86_PAE) |
if (k8_addr + rdev->mc.visible_vram_size < 0x100000000ULL) |
#endif |
{ |
/* FastFB shall be used with UMA memory. Here it is simply disabled when sideport |
* memory is present. |
*/ |
if (rdev->mc.igp_sideport_enabled == false && radeon_fastfb == 1) { |
DRM_INFO("Direct mapping: aper base at 0x%llx, replaced by direct mapping base 0x%llx.\n", |
(unsigned long long)rdev->mc.aper_base, k8_addr); |
rdev->mc.aper_base = (resource_size_t)k8_addr; |
rdev->fastfb_working = true; |
} |
} |
rs690_pm_info(rdev); |
radeon_vram_location(rdev, &rdev->mc, base); |
rdev->mc.gtt_base_align = rdev->mc.gtt_size - 1; |
628,6 → 651,12 |
} |
/* Enable IRQ */ |
if (!rdev->irq.installed) { |
r = radeon_irq_kms_init(rdev); |
if (r) |
return r; |
} |
rs600_irq_set(rdev); |
rdev->config.r300.hdp_cntl = RREG32(RADEON_HOST_PATH_CNTL); |
/* 1M ring buffer */ |
696,9 → 725,6 |
r = radeon_fence_driver_init(rdev); |
if (r) |
return r; |
r = radeon_irq_kms_init(rdev); |
if (r) |
return r; |
/* Memory manager */ |
r = radeon_bo_init(rdev); |
if (r) |
/drivers/video/drm/radeon/rs690d.h |
---|
29,6 → 29,9 |
#define __RS690D_H__ |
/* Registers */ |
#define R_00001E_K8_FB_LOCATION 0x00001E |
#define R_00005F_MC_MISC_UMA_CNTL 0x00005F |
#define G_00005F_K8_ADDR_EXT(x) (((x) >> 0) & 0xFF) |
#define R_000078_MC_INDEX 0x000078 |
#define S_000078_MC_IND_ADDR(x) (((x) & 0x1FF) << 0) |
#define G_000078_MC_IND_ADDR(x) (((x) >> 0) & 0x1FF) |
/drivers/video/drm/radeon/rv515.c |
---|
303,8 → 303,10 |
tmp = RREG32(AVIVO_D1CRTC_CONTROL + crtc_offsets[i]); |
if (!(tmp & AVIVO_CRTC_DISP_READ_REQUEST_DISABLE)) { |
radeon_wait_for_vblank(rdev, i); |
WREG32(AVIVO_D1CRTC_UPDATE_LOCK + crtc_offsets[i], 1); |
tmp |= AVIVO_CRTC_DISP_READ_REQUEST_DISABLE; |
WREG32(AVIVO_D1CRTC_CONTROL + crtc_offsets[i], tmp); |
WREG32(AVIVO_D1CRTC_UPDATE_LOCK + crtc_offsets[i], 0); |
} |
/* wait for the next frame */ |
frame_count = radeon_get_vblank_counter(rdev, i); |
313,6 → 315,15 |
break; |
udelay(1); |
} |
/* XXX this is a hack to avoid strange behavior with EFI on certain systems */ |
WREG32(AVIVO_D1CRTC_UPDATE_LOCK + crtc_offsets[i], 1); |
tmp = RREG32(AVIVO_D1CRTC_CONTROL + crtc_offsets[i]); |
tmp &= ~AVIVO_CRTC_EN; |
WREG32(AVIVO_D1CRTC_CONTROL + crtc_offsets[i], tmp); |
WREG32(AVIVO_D1CRTC_UPDATE_LOCK + crtc_offsets[i], 0); |
save->crtc_enabled[i] = false; |
/* ***** */ |
} else { |
save->crtc_enabled[i] = false; |
} |
336,7 → 347,25 |
WREG32(R600_CITF_CNTL, blackout); |
} |
} |
/* wait for the MC to settle */ |
udelay(100); |
/* lock double buffered regs */ |
for (i = 0; i < rdev->num_crtc; i++) { |
if (save->crtc_enabled[i]) { |
tmp = RREG32(AVIVO_D1GRPH_UPDATE + crtc_offsets[i]); |
if (!(tmp & AVIVO_D1GRPH_UPDATE_LOCK)) { |
tmp |= AVIVO_D1GRPH_UPDATE_LOCK; |
WREG32(AVIVO_D1GRPH_UPDATE + crtc_offsets[i], tmp); |
} |
tmp = RREG32(AVIVO_D1MODE_MASTER_UPDATE_LOCK + crtc_offsets[i]); |
if (!(tmp & 1)) { |
tmp |= 1; |
WREG32(AVIVO_D1MODE_MASTER_UPDATE_LOCK + crtc_offsets[i], tmp); |
} |
} |
} |
} |
void rv515_mc_resume(struct radeon_device *rdev, struct rv515_mc_save *save) |
{ |
346,7 → 375,7 |
/* update crtc base addresses */ |
for (i = 0; i < rdev->num_crtc; i++) { |
if (rdev->family >= CHIP_RV770) { |
if (i == 1) { |
if (i == 0) { |
WREG32(R700_D1GRPH_PRIMARY_SURFACE_ADDRESS_HIGH, |
upper_32_bits(rdev->mc.vram_start)); |
WREG32(R700_D1GRPH_SECONDARY_SURFACE_ADDRESS_HIGH, |
365,6 → 394,33 |
} |
WREG32(R_000310_VGA_MEMORY_BASE_ADDRESS, (u32)rdev->mc.vram_start); |
/* unlock regs and wait for update */ |
for (i = 0; i < rdev->num_crtc; i++) { |
if (save->crtc_enabled[i]) { |
tmp = RREG32(AVIVO_D1MODE_MASTER_UPDATE_MODE + crtc_offsets[i]); |
if ((tmp & 0x3) != 0) { |
tmp &= ~0x3; |
WREG32(AVIVO_D1MODE_MASTER_UPDATE_MODE + crtc_offsets[i], tmp); |
} |
tmp = RREG32(AVIVO_D1GRPH_UPDATE + crtc_offsets[i]); |
if (tmp & AVIVO_D1GRPH_UPDATE_LOCK) { |
tmp &= ~AVIVO_D1GRPH_UPDATE_LOCK; |
WREG32(AVIVO_D1GRPH_UPDATE + crtc_offsets[i], tmp); |
} |
tmp = RREG32(AVIVO_D1MODE_MASTER_UPDATE_LOCK + crtc_offsets[i]); |
if (tmp & 1) { |
tmp &= ~1; |
WREG32(AVIVO_D1MODE_MASTER_UPDATE_LOCK + crtc_offsets[i], tmp); |
} |
for (j = 0; j < rdev->usec_timeout; j++) { |
tmp = RREG32(AVIVO_D1GRPH_UPDATE + crtc_offsets[i]); |
if ((tmp & AVIVO_D1GRPH_SURFACE_UPDATE_PENDING) == 0) |
break; |
udelay(1); |
} |
} |
} |
if (rdev->family >= CHIP_R600) { |
/* unblackout the MC */ |
if (rdev->family >= CHIP_RV770) |
476,6 → 532,12 |
} |
/* Enable IRQ */ |
if (!rdev->irq.installed) { |
r = radeon_irq_kms_init(rdev); |
if (r) |
return r; |
} |
rs600_irq_set(rdev); |
rdev->config.r300.hdp_cntl = RREG32(RADEON_HOST_PATH_CNTL); |
/* 1M ring buffer */ |
551,9 → 613,6 |
r = radeon_fence_driver_init(rdev); |
if (r) |
return r; |
r = radeon_irq_kms_init(rdev); |
if (r) |
return r; |
/* Memory manager */ |
r = radeon_bo_init(rdev); |
if (r) |
568,11 → 627,6 |
if (r) { |
/* Somethings want wront with the accel init stop accel */ |
dev_err(rdev->dev, "Disabling GPU acceleration\n"); |
// r100_cp_fini(rdev); |
// r100_wb_fini(rdev); |
// r100_ib_fini(rdev); |
rv370_pcie_gart_fini(rdev); |
// radeon_agp_fini(rdev); |
rdev->accel_working = false; |
} |
return 0; |
/drivers/video/drm/radeon/rv515d.h |
---|
205,17 → 205,6 |
REG_SET(PACKET3_IT_OPCODE, (op)) | \ |
REG_SET(PACKET3_COUNT, (n))) |
#define PACKET_TYPE0 0 |
#define PACKET_TYPE1 1 |
#define PACKET_TYPE2 2 |
#define PACKET_TYPE3 3 |
#define CP_PACKET_GET_TYPE(h) (((h) >> 30) & 3) |
#define CP_PACKET_GET_COUNT(h) (((h) >> 16) & 0x3FFF) |
#define CP_PACKET0_GET_REG(h) (((h) & 0x1FFF) << 2) |
#define CP_PACKET0_GET_ONE_REG_WR(h) (((h) >> 15) & 1) |
#define CP_PACKET3_GET_OPCODE(h) (((h) >> 8) & 0xFF) |
/* Registers */ |
#define R_0000F0_RBBM_SOFT_RESET 0x0000F0 |
#define S_0000F0_SOFT_RESET_CP(x) (((x) & 0x1) << 0) |
/drivers/video/drm/radeon/rv770.c |
---|
42,8 → 42,843 |
static void rv770_gpu_init(struct radeon_device *rdev); |
void rv770_fini(struct radeon_device *rdev); |
static void rv770_pcie_gen2_enable(struct radeon_device *rdev); |
int evergreen_set_uvd_clocks(struct radeon_device *rdev, u32 vclk, u32 dclk); |
int rv770_set_uvd_clocks(struct radeon_device *rdev, u32 vclk, u32 dclk) |
{ |
unsigned fb_div = 0, vclk_div = 0, dclk_div = 0; |
int r; |
/* RV740 uses evergreen uvd clk programming */ |
if (rdev->family == CHIP_RV740) |
return evergreen_set_uvd_clocks(rdev, vclk, dclk); |
/* bypass vclk and dclk with bclk */ |
WREG32_P(CG_UPLL_FUNC_CNTL_2, |
VCLK_SRC_SEL(1) | DCLK_SRC_SEL(1), |
~(VCLK_SRC_SEL_MASK | DCLK_SRC_SEL_MASK)); |
if (!vclk || !dclk) { |
/* keep the Bypass mode, put PLL to sleep */ |
WREG32_P(CG_UPLL_FUNC_CNTL, UPLL_SLEEP_MASK, ~UPLL_SLEEP_MASK); |
return 0; |
} |
// r = radeon_uvd_calc_upll_dividers(rdev, vclk, dclk, 50000, 160000, |
// 43663, 0x03FFFFFE, 1, 30, ~0, |
// &fb_div, &vclk_div, &dclk_div); |
// if (r) |
return r; |
fb_div |= 1; |
vclk_div -= 1; |
dclk_div -= 1; |
/* set UPLL_FB_DIV to 0x50000 */ |
WREG32_P(CG_UPLL_FUNC_CNTL_3, UPLL_FB_DIV(0x50000), ~UPLL_FB_DIV_MASK); |
/* deassert UPLL_RESET and UPLL_SLEEP */ |
WREG32_P(CG_UPLL_FUNC_CNTL, 0, ~(UPLL_RESET_MASK | UPLL_SLEEP_MASK)); |
/* assert BYPASS EN and FB_DIV[0] <- ??? why? */ |
WREG32_P(CG_UPLL_FUNC_CNTL, UPLL_BYPASS_EN_MASK, ~UPLL_BYPASS_EN_MASK); |
WREG32_P(CG_UPLL_FUNC_CNTL_3, UPLL_FB_DIV(1), ~UPLL_FB_DIV(1)); |
// r = radeon_uvd_send_upll_ctlreq(rdev, CG_UPLL_FUNC_CNTL); |
// if (r) |
return r; |
/* assert PLL_RESET */ |
WREG32_P(CG_UPLL_FUNC_CNTL, UPLL_RESET_MASK, ~UPLL_RESET_MASK); |
/* set the required FB_DIV, REF_DIV, Post divder values */ |
WREG32_P(CG_UPLL_FUNC_CNTL, UPLL_REF_DIV(1), ~UPLL_REF_DIV_MASK); |
WREG32_P(CG_UPLL_FUNC_CNTL_2, |
UPLL_SW_HILEN(vclk_div >> 1) | |
UPLL_SW_LOLEN((vclk_div >> 1) + (vclk_div & 1)) | |
UPLL_SW_HILEN2(dclk_div >> 1) | |
UPLL_SW_LOLEN2((dclk_div >> 1) + (dclk_div & 1)), |
~UPLL_SW_MASK); |
WREG32_P(CG_UPLL_FUNC_CNTL_3, UPLL_FB_DIV(fb_div), |
~UPLL_FB_DIV_MASK); |
/* give the PLL some time to settle */ |
mdelay(15); |
/* deassert PLL_RESET */ |
WREG32_P(CG_UPLL_FUNC_CNTL, 0, ~UPLL_RESET_MASK); |
mdelay(15); |
/* deassert BYPASS EN and FB_DIV[0] <- ??? why? */ |
WREG32_P(CG_UPLL_FUNC_CNTL, 0, ~UPLL_BYPASS_EN_MASK); |
WREG32_P(CG_UPLL_FUNC_CNTL_3, 0, ~UPLL_FB_DIV(1)); |
// r = radeon_uvd_send_upll_ctlreq(rdev, CG_UPLL_FUNC_CNTL); |
// if (r) |
return r; |
/* switch VCLK and DCLK selection */ |
WREG32_P(CG_UPLL_FUNC_CNTL_2, |
VCLK_SRC_SEL(2) | DCLK_SRC_SEL(2), |
~(VCLK_SRC_SEL_MASK | DCLK_SRC_SEL_MASK)); |
mdelay(100); |
return 0; |
} |
static const u32 r7xx_golden_registers[] = |
{ |
0x8d00, 0xffffffff, 0x0e0e0074, |
0x8d04, 0xffffffff, 0x013a2b34, |
0x9508, 0xffffffff, 0x00000002, |
0x8b20, 0xffffffff, 0, |
0x88c4, 0xffffffff, 0x000000c2, |
0x28350, 0xffffffff, 0, |
0x9058, 0xffffffff, 0x0fffc40f, |
0x240c, 0xffffffff, 0x00000380, |
0x733c, 0xffffffff, 0x00000002, |
0x2650, 0x00040000, 0, |
0x20bc, 0x00040000, 0, |
0x7300, 0xffffffff, 0x001000f0 |
}; |
static const u32 r7xx_golden_dyn_gpr_registers[] = |
{ |
0x8db0, 0xffffffff, 0x98989898, |
0x8db4, 0xffffffff, 0x98989898, |
0x8db8, 0xffffffff, 0x98989898, |
0x8dbc, 0xffffffff, 0x98989898, |
0x8dc0, 0xffffffff, 0x98989898, |
0x8dc4, 0xffffffff, 0x98989898, |
0x8dc8, 0xffffffff, 0x98989898, |
0x8dcc, 0xffffffff, 0x98989898, |
0x88c4, 0xffffffff, 0x00000082 |
}; |
static const u32 rv770_golden_registers[] = |
{ |
0x562c, 0xffffffff, 0, |
0x3f90, 0xffffffff, 0, |
0x9148, 0xffffffff, 0, |
0x3f94, 0xffffffff, 0, |
0x914c, 0xffffffff, 0, |
0x9698, 0x18000000, 0x18000000 |
}; |
static const u32 rv770ce_golden_registers[] = |
{ |
0x562c, 0xffffffff, 0, |
0x3f90, 0xffffffff, 0x00cc0000, |
0x9148, 0xffffffff, 0x00cc0000, |
0x3f94, 0xffffffff, 0x00cc0000, |
0x914c, 0xffffffff, 0x00cc0000, |
0x9b7c, 0xffffffff, 0x00fa0000, |
0x3f8c, 0xffffffff, 0x00fa0000, |
0x9698, 0x18000000, 0x18000000 |
}; |
static const u32 rv770_mgcg_init[] = |
{ |
0x8bcc, 0xffffffff, 0x130300f9, |
0x5448, 0xffffffff, 0x100, |
0x55e4, 0xffffffff, 0x100, |
0x160c, 0xffffffff, 0x100, |
0x5644, 0xffffffff, 0x100, |
0xc164, 0xffffffff, 0x100, |
0x8a18, 0xffffffff, 0x100, |
0x897c, 0xffffffff, 0x8000100, |
0x8b28, 0xffffffff, 0x3c000100, |
0x9144, 0xffffffff, 0x100, |
0x9a1c, 0xffffffff, 0x10000, |
0x9a50, 0xffffffff, 0x100, |
0x9a1c, 0xffffffff, 0x10001, |
0x9a50, 0xffffffff, 0x100, |
0x9a1c, 0xffffffff, 0x10002, |
0x9a50, 0xffffffff, 0x100, |
0x9a1c, 0xffffffff, 0x10003, |
0x9a50, 0xffffffff, 0x100, |
0x9a1c, 0xffffffff, 0x0, |
0x9870, 0xffffffff, 0x100, |
0x8d58, 0xffffffff, 0x100, |
0x9500, 0xffffffff, 0x0, |
0x9510, 0xffffffff, 0x100, |
0x9500, 0xffffffff, 0x1, |
0x9510, 0xffffffff, 0x100, |
0x9500, 0xffffffff, 0x2, |
0x9510, 0xffffffff, 0x100, |
0x9500, 0xffffffff, 0x3, |
0x9510, 0xffffffff, 0x100, |
0x9500, 0xffffffff, 0x4, |
0x9510, 0xffffffff, 0x100, |
0x9500, 0xffffffff, 0x5, |
0x9510, 0xffffffff, 0x100, |
0x9500, 0xffffffff, 0x6, |
0x9510, 0xffffffff, 0x100, |
0x9500, 0xffffffff, 0x7, |
0x9510, 0xffffffff, 0x100, |
0x9500, 0xffffffff, 0x8, |
0x9510, 0xffffffff, 0x100, |
0x9500, 0xffffffff, 0x9, |
0x9510, 0xffffffff, 0x100, |
0x9500, 0xffffffff, 0x8000, |
0x9490, 0xffffffff, 0x0, |
0x949c, 0xffffffff, 0x100, |
0x9490, 0xffffffff, 0x1, |
0x949c, 0xffffffff, 0x100, |
0x9490, 0xffffffff, 0x2, |
0x949c, 0xffffffff, 0x100, |
0x9490, 0xffffffff, 0x3, |
0x949c, 0xffffffff, 0x100, |
0x9490, 0xffffffff, 0x4, |
0x949c, 0xffffffff, 0x100, |
0x9490, 0xffffffff, 0x5, |
0x949c, 0xffffffff, 0x100, |
0x9490, 0xffffffff, 0x6, |
0x949c, 0xffffffff, 0x100, |
0x9490, 0xffffffff, 0x7, |
0x949c, 0xffffffff, 0x100, |
0x9490, 0xffffffff, 0x8, |
0x949c, 0xffffffff, 0x100, |
0x9490, 0xffffffff, 0x9, |
0x949c, 0xffffffff, 0x100, |
0x9490, 0xffffffff, 0x8000, |
0x9604, 0xffffffff, 0x0, |
0x9654, 0xffffffff, 0x100, |
0x9604, 0xffffffff, 0x1, |
0x9654, 0xffffffff, 0x100, |
0x9604, 0xffffffff, 0x2, |
0x9654, 0xffffffff, 0x100, |
0x9604, 0xffffffff, 0x3, |
0x9654, 0xffffffff, 0x100, |
0x9604, 0xffffffff, 0x4, |
0x9654, 0xffffffff, 0x100, |
0x9604, 0xffffffff, 0x5, |
0x9654, 0xffffffff, 0x100, |
0x9604, 0xffffffff, 0x6, |
0x9654, 0xffffffff, 0x100, |
0x9604, 0xffffffff, 0x7, |
0x9654, 0xffffffff, 0x100, |
0x9604, 0xffffffff, 0x8, |
0x9654, 0xffffffff, 0x100, |
0x9604, 0xffffffff, 0x9, |
0x9654, 0xffffffff, 0x100, |
0x9604, 0xffffffff, 0x80000000, |
0x9030, 0xffffffff, 0x100, |
0x9034, 0xffffffff, 0x100, |
0x9038, 0xffffffff, 0x100, |
0x903c, 0xffffffff, 0x100, |
0x9040, 0xffffffff, 0x100, |
0xa200, 0xffffffff, 0x100, |
0xa204, 0xffffffff, 0x100, |
0xa208, 0xffffffff, 0x100, |
0xa20c, 0xffffffff, 0x100, |
0x971c, 0xffffffff, 0x100, |
0x915c, 0xffffffff, 0x00020001, |
0x9160, 0xffffffff, 0x00040003, |
0x916c, 0xffffffff, 0x00060005, |
0x9170, 0xffffffff, 0x00080007, |
0x9174, 0xffffffff, 0x000a0009, |
0x9178, 0xffffffff, 0x000c000b, |
0x917c, 0xffffffff, 0x000e000d, |
0x9180, 0xffffffff, 0x0010000f, |
0x918c, 0xffffffff, 0x00120011, |
0x9190, 0xffffffff, 0x00140013, |
0x9194, 0xffffffff, 0x00020001, |
0x9198, 0xffffffff, 0x00040003, |
0x919c, 0xffffffff, 0x00060005, |
0x91a8, 0xffffffff, 0x00080007, |
0x91ac, 0xffffffff, 0x000a0009, |
0x91b0, 0xffffffff, 0x000c000b, |
0x91b4, 0xffffffff, 0x000e000d, |
0x91b8, 0xffffffff, 0x0010000f, |
0x91c4, 0xffffffff, 0x00120011, |
0x91c8, 0xffffffff, 0x00140013, |
0x91cc, 0xffffffff, 0x00020001, |
0x91d0, 0xffffffff, 0x00040003, |
0x91d4, 0xffffffff, 0x00060005, |
0x91e0, 0xffffffff, 0x00080007, |
0x91e4, 0xffffffff, 0x000a0009, |
0x91e8, 0xffffffff, 0x000c000b, |
0x91ec, 0xffffffff, 0x00020001, |
0x91f0, 0xffffffff, 0x00040003, |
0x91f4, 0xffffffff, 0x00060005, |
0x9200, 0xffffffff, 0x00080007, |
0x9204, 0xffffffff, 0x000a0009, |
0x9208, 0xffffffff, 0x000c000b, |
0x920c, 0xffffffff, 0x000e000d, |
0x9210, 0xffffffff, 0x0010000f, |
0x921c, 0xffffffff, 0x00120011, |
0x9220, 0xffffffff, 0x00140013, |
0x9224, 0xffffffff, 0x00020001, |
0x9228, 0xffffffff, 0x00040003, |
0x922c, 0xffffffff, 0x00060005, |
0x9238, 0xffffffff, 0x00080007, |
0x923c, 0xffffffff, 0x000a0009, |
0x9240, 0xffffffff, 0x000c000b, |
0x9244, 0xffffffff, 0x000e000d, |
0x9248, 0xffffffff, 0x0010000f, |
0x9254, 0xffffffff, 0x00120011, |
0x9258, 0xffffffff, 0x00140013, |
0x925c, 0xffffffff, 0x00020001, |
0x9260, 0xffffffff, 0x00040003, |
0x9264, 0xffffffff, 0x00060005, |
0x9270, 0xffffffff, 0x00080007, |
0x9274, 0xffffffff, 0x000a0009, |
0x9278, 0xffffffff, 0x000c000b, |
0x927c, 0xffffffff, 0x000e000d, |
0x9280, 0xffffffff, 0x0010000f, |
0x928c, 0xffffffff, 0x00120011, |
0x9290, 0xffffffff, 0x00140013, |
0x9294, 0xffffffff, 0x00020001, |
0x929c, 0xffffffff, 0x00040003, |
0x92a0, 0xffffffff, 0x00060005, |
0x92a4, 0xffffffff, 0x00080007 |
}; |
static const u32 rv710_golden_registers[] = |
{ |
0x3f90, 0x00ff0000, 0x00fc0000, |
0x9148, 0x00ff0000, 0x00fc0000, |
0x3f94, 0x00ff0000, 0x00fc0000, |
0x914c, 0x00ff0000, 0x00fc0000, |
0xb4c, 0x00000020, 0x00000020, |
0xa180, 0xffffffff, 0x00003f3f |
}; |
static const u32 rv710_mgcg_init[] = |
{ |
0x8bcc, 0xffffffff, 0x13030040, |
0x5448, 0xffffffff, 0x100, |
0x55e4, 0xffffffff, 0x100, |
0x160c, 0xffffffff, 0x100, |
0x5644, 0xffffffff, 0x100, |
0xc164, 0xffffffff, 0x100, |
0x8a18, 0xffffffff, 0x100, |
0x897c, 0xffffffff, 0x8000100, |
0x8b28, 0xffffffff, 0x3c000100, |
0x9144, 0xffffffff, 0x100, |
0x9a1c, 0xffffffff, 0x10000, |
0x9a50, 0xffffffff, 0x100, |
0x9a1c, 0xffffffff, 0x0, |
0x9870, 0xffffffff, 0x100, |
0x8d58, 0xffffffff, 0x100, |
0x9500, 0xffffffff, 0x0, |
0x9510, 0xffffffff, 0x100, |
0x9500, 0xffffffff, 0x1, |
0x9510, 0xffffffff, 0x100, |
0x9500, 0xffffffff, 0x8000, |
0x9490, 0xffffffff, 0x0, |
0x949c, 0xffffffff, 0x100, |
0x9490, 0xffffffff, 0x1, |
0x949c, 0xffffffff, 0x100, |
0x9490, 0xffffffff, 0x8000, |
0x9604, 0xffffffff, 0x0, |
0x9654, 0xffffffff, 0x100, |
0x9604, 0xffffffff, 0x1, |
0x9654, 0xffffffff, 0x100, |
0x9604, 0xffffffff, 0x80000000, |
0x9030, 0xffffffff, 0x100, |
0x9034, 0xffffffff, 0x100, |
0x9038, 0xffffffff, 0x100, |
0x903c, 0xffffffff, 0x100, |
0x9040, 0xffffffff, 0x100, |
0xa200, 0xffffffff, 0x100, |
0xa204, 0xffffffff, 0x100, |
0xa208, 0xffffffff, 0x100, |
0xa20c, 0xffffffff, 0x100, |
0x971c, 0xffffffff, 0x100, |
0x915c, 0xffffffff, 0x00020001, |
0x9174, 0xffffffff, 0x00000003, |
0x9178, 0xffffffff, 0x00050001, |
0x917c, 0xffffffff, 0x00030002, |
0x918c, 0xffffffff, 0x00000004, |
0x9190, 0xffffffff, 0x00070006, |
0x9194, 0xffffffff, 0x00050001, |
0x9198, 0xffffffff, 0x00030002, |
0x91a8, 0xffffffff, 0x00000004, |
0x91ac, 0xffffffff, 0x00070006, |
0x91e8, 0xffffffff, 0x00000001, |
0x9294, 0xffffffff, 0x00000001, |
0x929c, 0xffffffff, 0x00000002, |
0x92a0, 0xffffffff, 0x00040003, |
0x9150, 0xffffffff, 0x4d940000 |
}; |
static const u32 rv730_golden_registers[] = |
{ |
0x3f90, 0x00ff0000, 0x00f00000, |
0x9148, 0x00ff0000, 0x00f00000, |
0x3f94, 0x00ff0000, 0x00f00000, |
0x914c, 0x00ff0000, 0x00f00000, |
0x900c, 0xffffffff, 0x003b033f, |
0xb4c, 0x00000020, 0x00000020, |
0xa180, 0xffffffff, 0x00003f3f |
}; |
static const u32 rv730_mgcg_init[] = |
{ |
0x8bcc, 0xffffffff, 0x130300f9, |
0x5448, 0xffffffff, 0x100, |
0x55e4, 0xffffffff, 0x100, |
0x160c, 0xffffffff, 0x100, |
0x5644, 0xffffffff, 0x100, |
0xc164, 0xffffffff, 0x100, |
0x8a18, 0xffffffff, 0x100, |
0x897c, 0xffffffff, 0x8000100, |
0x8b28, 0xffffffff, 0x3c000100, |
0x9144, 0xffffffff, 0x100, |
0x9a1c, 0xffffffff, 0x10000, |
0x9a50, 0xffffffff, 0x100, |
0x9a1c, 0xffffffff, 0x10001, |
0x9a50, 0xffffffff, 0x100, |
0x9a1c, 0xffffffff, 0x0, |
0x9870, 0xffffffff, 0x100, |
0x8d58, 0xffffffff, 0x100, |
0x9500, 0xffffffff, 0x0, |
0x9510, 0xffffffff, 0x100, |
0x9500, 0xffffffff, 0x1, |
0x9510, 0xffffffff, 0x100, |
0x9500, 0xffffffff, 0x2, |
0x9510, 0xffffffff, 0x100, |
0x9500, 0xffffffff, 0x3, |
0x9510, 0xffffffff, 0x100, |
0x9500, 0xffffffff, 0x4, |
0x9510, 0xffffffff, 0x100, |
0x9500, 0xffffffff, 0x5, |
0x9510, 0xffffffff, 0x100, |
0x9500, 0xffffffff, 0x6, |
0x9510, 0xffffffff, 0x100, |
0x9500, 0xffffffff, 0x7, |
0x9510, 0xffffffff, 0x100, |
0x9500, 0xffffffff, 0x8000, |
0x9490, 0xffffffff, 0x0, |
0x949c, 0xffffffff, 0x100, |
0x9490, 0xffffffff, 0x1, |
0x949c, 0xffffffff, 0x100, |
0x9490, 0xffffffff, 0x2, |
0x949c, 0xffffffff, 0x100, |
0x9490, 0xffffffff, 0x3, |
0x949c, 0xffffffff, 0x100, |
0x9490, 0xffffffff, 0x4, |
0x949c, 0xffffffff, 0x100, |
0x9490, 0xffffffff, 0x5, |
0x949c, 0xffffffff, 0x100, |
0x9490, 0xffffffff, 0x6, |
0x949c, 0xffffffff, 0x100, |
0x9490, 0xffffffff, 0x7, |
0x949c, 0xffffffff, 0x100, |
0x9490, 0xffffffff, 0x8000, |
0x9604, 0xffffffff, 0x0, |
0x9654, 0xffffffff, 0x100, |
0x9604, 0xffffffff, 0x1, |
0x9654, 0xffffffff, 0x100, |
0x9604, 0xffffffff, 0x2, |
0x9654, 0xffffffff, 0x100, |
0x9604, 0xffffffff, 0x3, |
0x9654, 0xffffffff, 0x100, |
0x9604, 0xffffffff, 0x4, |
0x9654, 0xffffffff, 0x100, |
0x9604, 0xffffffff, 0x5, |
0x9654, 0xffffffff, 0x100, |
0x9604, 0xffffffff, 0x6, |
0x9654, 0xffffffff, 0x100, |
0x9604, 0xffffffff, 0x7, |
0x9654, 0xffffffff, 0x100, |
0x9604, 0xffffffff, 0x80000000, |
0x9030, 0xffffffff, 0x100, |
0x9034, 0xffffffff, 0x100, |
0x9038, 0xffffffff, 0x100, |
0x903c, 0xffffffff, 0x100, |
0x9040, 0xffffffff, 0x100, |
0xa200, 0xffffffff, 0x100, |
0xa204, 0xffffffff, 0x100, |
0xa208, 0xffffffff, 0x100, |
0xa20c, 0xffffffff, 0x100, |
0x971c, 0xffffffff, 0x100, |
0x915c, 0xffffffff, 0x00020001, |
0x916c, 0xffffffff, 0x00040003, |
0x9170, 0xffffffff, 0x00000005, |
0x9178, 0xffffffff, 0x00050001, |
0x917c, 0xffffffff, 0x00030002, |
0x918c, 0xffffffff, 0x00000004, |
0x9190, 0xffffffff, 0x00070006, |
0x9194, 0xffffffff, 0x00050001, |
0x9198, 0xffffffff, 0x00030002, |
0x91a8, 0xffffffff, 0x00000004, |
0x91ac, 0xffffffff, 0x00070006, |
0x91b0, 0xffffffff, 0x00050001, |
0x91b4, 0xffffffff, 0x00030002, |
0x91c4, 0xffffffff, 0x00000004, |
0x91c8, 0xffffffff, 0x00070006, |
0x91cc, 0xffffffff, 0x00050001, |
0x91d0, 0xffffffff, 0x00030002, |
0x91e0, 0xffffffff, 0x00000004, |
0x91e4, 0xffffffff, 0x00070006, |
0x91e8, 0xffffffff, 0x00000001, |
0x91ec, 0xffffffff, 0x00050001, |
0x91f0, 0xffffffff, 0x00030002, |
0x9200, 0xffffffff, 0x00000004, |
0x9204, 0xffffffff, 0x00070006, |
0x9208, 0xffffffff, 0x00050001, |
0x920c, 0xffffffff, 0x00030002, |
0x921c, 0xffffffff, 0x00000004, |
0x9220, 0xffffffff, 0x00070006, |
0x9224, 0xffffffff, 0x00050001, |
0x9228, 0xffffffff, 0x00030002, |
0x9238, 0xffffffff, 0x00000004, |
0x923c, 0xffffffff, 0x00070006, |
0x9240, 0xffffffff, 0x00050001, |
0x9244, 0xffffffff, 0x00030002, |
0x9254, 0xffffffff, 0x00000004, |
0x9258, 0xffffffff, 0x00070006, |
0x9294, 0xffffffff, 0x00000001, |
0x929c, 0xffffffff, 0x00000002, |
0x92a0, 0xffffffff, 0x00040003, |
0x92a4, 0xffffffff, 0x00000005 |
}; |
static const u32 rv740_golden_registers[] = |
{ |
0x88c4, 0xffffffff, 0x00000082, |
0x28a50, 0xfffffffc, 0x00000004, |
0x2650, 0x00040000, 0, |
0x20bc, 0x00040000, 0, |
0x733c, 0xffffffff, 0x00000002, |
0x7300, 0xffffffff, 0x001000f0, |
0x3f90, 0x00ff0000, 0, |
0x9148, 0x00ff0000, 0, |
0x3f94, 0x00ff0000, 0, |
0x914c, 0x00ff0000, 0, |
0x240c, 0xffffffff, 0x00000380, |
0x8a14, 0x00000007, 0x00000007, |
0x8b24, 0xffffffff, 0x00ff0fff, |
0x28a4c, 0xffffffff, 0x00004000, |
0xa180, 0xffffffff, 0x00003f3f, |
0x8d00, 0xffffffff, 0x0e0e003a, |
0x8d04, 0xffffffff, 0x013a0e2a, |
0x8c00, 0xffffffff, 0xe400000f, |
0x8db0, 0xffffffff, 0x98989898, |
0x8db4, 0xffffffff, 0x98989898, |
0x8db8, 0xffffffff, 0x98989898, |
0x8dbc, 0xffffffff, 0x98989898, |
0x8dc0, 0xffffffff, 0x98989898, |
0x8dc4, 0xffffffff, 0x98989898, |
0x8dc8, 0xffffffff, 0x98989898, |
0x8dcc, 0xffffffff, 0x98989898, |
0x9058, 0xffffffff, 0x0fffc40f, |
0x900c, 0xffffffff, 0x003b033f, |
0x28350, 0xffffffff, 0, |
0x8cf0, 0x1fffffff, 0x08e00420, |
0x9508, 0xffffffff, 0x00000002, |
0x88c4, 0xffffffff, 0x000000c2, |
0x9698, 0x18000000, 0x18000000 |
}; |
static const u32 rv740_mgcg_init[] = |
{ |
0x8bcc, 0xffffffff, 0x13030100, |
0x5448, 0xffffffff, 0x100, |
0x55e4, 0xffffffff, 0x100, |
0x160c, 0xffffffff, 0x100, |
0x5644, 0xffffffff, 0x100, |
0xc164, 0xffffffff, 0x100, |
0x8a18, 0xffffffff, 0x100, |
0x897c, 0xffffffff, 0x100, |
0x8b28, 0xffffffff, 0x100, |
0x9144, 0xffffffff, 0x100, |
0x9a1c, 0xffffffff, 0x10000, |
0x9a50, 0xffffffff, 0x100, |
0x9a1c, 0xffffffff, 0x10001, |
0x9a50, 0xffffffff, 0x100, |
0x9a1c, 0xffffffff, 0x10002, |
0x9a50, 0xffffffff, 0x100, |
0x9a1c, 0xffffffff, 0x10003, |
0x9a50, 0xffffffff, 0x100, |
0x9a1c, 0xffffffff, 0x0, |
0x9870, 0xffffffff, 0x100, |
0x8d58, 0xffffffff, 0x100, |
0x9500, 0xffffffff, 0x0, |
0x9510, 0xffffffff, 0x100, |
0x9500, 0xffffffff, 0x1, |
0x9510, 0xffffffff, 0x100, |
0x9500, 0xffffffff, 0x2, |
0x9510, 0xffffffff, 0x100, |
0x9500, 0xffffffff, 0x3, |
0x9510, 0xffffffff, 0x100, |
0x9500, 0xffffffff, 0x4, |
0x9510, 0xffffffff, 0x100, |
0x9500, 0xffffffff, 0x5, |
0x9510, 0xffffffff, 0x100, |
0x9500, 0xffffffff, 0x6, |
0x9510, 0xffffffff, 0x100, |
0x9500, 0xffffffff, 0x7, |
0x9510, 0xffffffff, 0x100, |
0x9500, 0xffffffff, 0x8000, |
0x9490, 0xffffffff, 0x0, |
0x949c, 0xffffffff, 0x100, |
0x9490, 0xffffffff, 0x1, |
0x949c, 0xffffffff, 0x100, |
0x9490, 0xffffffff, 0x2, |
0x949c, 0xffffffff, 0x100, |
0x9490, 0xffffffff, 0x3, |
0x949c, 0xffffffff, 0x100, |
0x9490, 0xffffffff, 0x4, |
0x949c, 0xffffffff, 0x100, |
0x9490, 0xffffffff, 0x5, |
0x949c, 0xffffffff, 0x100, |
0x9490, 0xffffffff, 0x6, |
0x949c, 0xffffffff, 0x100, |
0x9490, 0xffffffff, 0x7, |
0x949c, 0xffffffff, 0x100, |
0x9490, 0xffffffff, 0x8000, |
0x9604, 0xffffffff, 0x0, |
0x9654, 0xffffffff, 0x100, |
0x9604, 0xffffffff, 0x1, |
0x9654, 0xffffffff, 0x100, |
0x9604, 0xffffffff, 0x2, |
0x9654, 0xffffffff, 0x100, |
0x9604, 0xffffffff, 0x3, |
0x9654, 0xffffffff, 0x100, |
0x9604, 0xffffffff, 0x4, |
0x9654, 0xffffffff, 0x100, |
0x9604, 0xffffffff, 0x5, |
0x9654, 0xffffffff, 0x100, |
0x9604, 0xffffffff, 0x6, |
0x9654, 0xffffffff, 0x100, |
0x9604, 0xffffffff, 0x7, |
0x9654, 0xffffffff, 0x100, |
0x9604, 0xffffffff, 0x80000000, |
0x9030, 0xffffffff, 0x100, |
0x9034, 0xffffffff, 0x100, |
0x9038, 0xffffffff, 0x100, |
0x903c, 0xffffffff, 0x100, |
0x9040, 0xffffffff, 0x100, |
0xa200, 0xffffffff, 0x100, |
0xa204, 0xffffffff, 0x100, |
0xa208, 0xffffffff, 0x100, |
0xa20c, 0xffffffff, 0x100, |
0x971c, 0xffffffff, 0x100, |
0x915c, 0xffffffff, 0x00020001, |
0x9160, 0xffffffff, 0x00040003, |
0x916c, 0xffffffff, 0x00060005, |
0x9170, 0xffffffff, 0x00080007, |
0x9174, 0xffffffff, 0x000a0009, |
0x9178, 0xffffffff, 0x000c000b, |
0x917c, 0xffffffff, 0x000e000d, |
0x9180, 0xffffffff, 0x0010000f, |
0x918c, 0xffffffff, 0x00120011, |
0x9190, 0xffffffff, 0x00140013, |
0x9194, 0xffffffff, 0x00020001, |
0x9198, 0xffffffff, 0x00040003, |
0x919c, 0xffffffff, 0x00060005, |
0x91a8, 0xffffffff, 0x00080007, |
0x91ac, 0xffffffff, 0x000a0009, |
0x91b0, 0xffffffff, 0x000c000b, |
0x91b4, 0xffffffff, 0x000e000d, |
0x91b8, 0xffffffff, 0x0010000f, |
0x91c4, 0xffffffff, 0x00120011, |
0x91c8, 0xffffffff, 0x00140013, |
0x91cc, 0xffffffff, 0x00020001, |
0x91d0, 0xffffffff, 0x00040003, |
0x91d4, 0xffffffff, 0x00060005, |
0x91e0, 0xffffffff, 0x00080007, |
0x91e4, 0xffffffff, 0x000a0009, |
0x91e8, 0xffffffff, 0x000c000b, |
0x91ec, 0xffffffff, 0x00020001, |
0x91f0, 0xffffffff, 0x00040003, |
0x91f4, 0xffffffff, 0x00060005, |
0x9200, 0xffffffff, 0x00080007, |
0x9204, 0xffffffff, 0x000a0009, |
0x9208, 0xffffffff, 0x000c000b, |
0x920c, 0xffffffff, 0x000e000d, |
0x9210, 0xffffffff, 0x0010000f, |
0x921c, 0xffffffff, 0x00120011, |
0x9220, 0xffffffff, 0x00140013, |
0x9224, 0xffffffff, 0x00020001, |
0x9228, 0xffffffff, 0x00040003, |
0x922c, 0xffffffff, 0x00060005, |
0x9238, 0xffffffff, 0x00080007, |
0x923c, 0xffffffff, 0x000a0009, |
0x9240, 0xffffffff, 0x000c000b, |
0x9244, 0xffffffff, 0x000e000d, |
0x9248, 0xffffffff, 0x0010000f, |
0x9254, 0xffffffff, 0x00120011, |
0x9258, 0xffffffff, 0x00140013, |
0x9294, 0xffffffff, 0x00020001, |
0x929c, 0xffffffff, 0x00040003, |
0x92a0, 0xffffffff, 0x00060005, |
0x92a4, 0xffffffff, 0x00080007 |
}; |
static void rv770_init_golden_registers(struct radeon_device *rdev) |
{ |
switch (rdev->family) { |
case CHIP_RV770: |
radeon_program_register_sequence(rdev, |
r7xx_golden_registers, |
(const u32)ARRAY_SIZE(r7xx_golden_registers)); |
radeon_program_register_sequence(rdev, |
r7xx_golden_dyn_gpr_registers, |
(const u32)ARRAY_SIZE(r7xx_golden_dyn_gpr_registers)); |
if (rdev->pdev->device == 0x994e) |
radeon_program_register_sequence(rdev, |
rv770ce_golden_registers, |
(const u32)ARRAY_SIZE(rv770ce_golden_registers)); |
else |
radeon_program_register_sequence(rdev, |
rv770_golden_registers, |
(const u32)ARRAY_SIZE(rv770_golden_registers)); |
radeon_program_register_sequence(rdev, |
rv770_mgcg_init, |
(const u32)ARRAY_SIZE(rv770_mgcg_init)); |
break; |
case CHIP_RV730: |
radeon_program_register_sequence(rdev, |
r7xx_golden_registers, |
(const u32)ARRAY_SIZE(r7xx_golden_registers)); |
radeon_program_register_sequence(rdev, |
r7xx_golden_dyn_gpr_registers, |
(const u32)ARRAY_SIZE(r7xx_golden_dyn_gpr_registers)); |
radeon_program_register_sequence(rdev, |
rv730_golden_registers, |
(const u32)ARRAY_SIZE(rv770_golden_registers)); |
radeon_program_register_sequence(rdev, |
rv730_mgcg_init, |
(const u32)ARRAY_SIZE(rv770_mgcg_init)); |
break; |
case CHIP_RV710: |
radeon_program_register_sequence(rdev, |
r7xx_golden_registers, |
(const u32)ARRAY_SIZE(r7xx_golden_registers)); |
radeon_program_register_sequence(rdev, |
r7xx_golden_dyn_gpr_registers, |
(const u32)ARRAY_SIZE(r7xx_golden_dyn_gpr_registers)); |
radeon_program_register_sequence(rdev, |
rv710_golden_registers, |
(const u32)ARRAY_SIZE(rv770_golden_registers)); |
radeon_program_register_sequence(rdev, |
rv710_mgcg_init, |
(const u32)ARRAY_SIZE(rv770_mgcg_init)); |
break; |
case CHIP_RV740: |
radeon_program_register_sequence(rdev, |
rv740_golden_registers, |
(const u32)ARRAY_SIZE(rv770_golden_registers)); |
radeon_program_register_sequence(rdev, |
rv740_mgcg_init, |
(const u32)ARRAY_SIZE(rv770_mgcg_init)); |
break; |
default: |
break; |
} |
} |
#define PCIE_BUS_CLK 10000 |
#define TCLK (PCIE_BUS_CLK / 10) |
/** |
* rv770_get_xclk - get the xclk |
* |
* @rdev: radeon_device pointer |
* |
* Returns the reference clock used by the gfx engine |
* (r7xx-cayman). |
*/ |
u32 rv770_get_xclk(struct radeon_device *rdev) |
{ |
u32 reference_clock = rdev->clock.spll.reference_freq; |
u32 tmp = RREG32(CG_CLKPIN_CNTL); |
if (tmp & MUX_TCLK_TO_XCLK) |
return TCLK; |
if (tmp & XTALIN_DIVIDE) |
return reference_clock / 4; |
return reference_clock; |
} |
u32 rv770_page_flip(struct radeon_device *rdev, int crtc_id, u64 crtc_base) |
{ |
struct radeon_crtc *radeon_crtc = rdev->mode_info.crtcs[crtc_id]; |
u32 tmp = RREG32(AVIVO_D1GRPH_UPDATE + radeon_crtc->crtc_offset); |
int i; |
/* Lock the graphics update lock */ |
tmp |= AVIVO_D1GRPH_UPDATE_LOCK; |
WREG32(AVIVO_D1GRPH_UPDATE + radeon_crtc->crtc_offset, tmp); |
/* update the scanout addresses */ |
if (radeon_crtc->crtc_id) { |
WREG32(D2GRPH_SECONDARY_SURFACE_ADDRESS_HIGH, upper_32_bits(crtc_base)); |
WREG32(D2GRPH_PRIMARY_SURFACE_ADDRESS_HIGH, upper_32_bits(crtc_base)); |
} else { |
WREG32(D1GRPH_SECONDARY_SURFACE_ADDRESS_HIGH, upper_32_bits(crtc_base)); |
WREG32(D1GRPH_PRIMARY_SURFACE_ADDRESS_HIGH, upper_32_bits(crtc_base)); |
} |
WREG32(D1GRPH_SECONDARY_SURFACE_ADDRESS + radeon_crtc->crtc_offset, |
(u32)crtc_base); |
WREG32(D1GRPH_PRIMARY_SURFACE_ADDRESS + radeon_crtc->crtc_offset, |
(u32)crtc_base); |
/* Wait for update_pending to go high. */ |
for (i = 0; i < rdev->usec_timeout; i++) { |
if (RREG32(AVIVO_D1GRPH_UPDATE + radeon_crtc->crtc_offset) & AVIVO_D1GRPH_SURFACE_UPDATE_PENDING) |
break; |
udelay(1); |
} |
DRM_DEBUG("Update pending now high. Unlocking vupdate_lock.\n"); |
/* Unlock the lock, so double-buffering can take place inside vblank */ |
tmp &= ~AVIVO_D1GRPH_UPDATE_LOCK; |
WREG32(AVIVO_D1GRPH_UPDATE + radeon_crtc->crtc_offset, tmp); |
/* Return current update_pending status: */ |
return RREG32(AVIVO_D1GRPH_UPDATE + radeon_crtc->crtc_offset) & AVIVO_D1GRPH_SURFACE_UPDATE_PENDING; |
} |
/* get temperature in millidegrees */ |
int rv770_get_temp(struct radeon_device *rdev) |
{ |
u32 temp = (RREG32(CG_MULT_THERMAL_STATUS) & ASIC_T_MASK) >> |
ASIC_T_SHIFT; |
int actual_temp; |
if (temp & 0x400) |
actual_temp = -256; |
else if (temp & 0x200) |
actual_temp = 255; |
else if (temp & 0x100) { |
actual_temp = temp & 0x1ff; |
actual_temp |= ~0x1ff; |
} else |
actual_temp = temp & 0xff; |
return (actual_temp * 1000) / 2; |
} |
void rv770_pm_misc(struct radeon_device *rdev) |
{ |
int req_ps_idx = rdev->pm.requested_power_state_index; |
int req_cm_idx = rdev->pm.requested_clock_mode_index; |
struct radeon_power_state *ps = &rdev->pm.power_state[req_ps_idx]; |
struct radeon_voltage *voltage = &ps->clock_info[req_cm_idx].voltage; |
if ((voltage->type == VOLTAGE_SW) && voltage->voltage) { |
/* 0xff01 is a flag rather then an actual voltage */ |
if (voltage->voltage == 0xff01) |
return; |
if (voltage->voltage != rdev->pm.current_vddc) { |
radeon_atom_set_voltage(rdev, voltage->voltage, SET_VOLTAGE_TYPE_ASIC_VDDC); |
rdev->pm.current_vddc = voltage->voltage; |
DRM_DEBUG("Setting: v: %d\n", voltage->voltage); |
} |
} |
} |
/* |
* GART |
*/ |
502,6 → 1337,11 |
WREG32(HDP_TILING_CONFIG, (gb_tiling_config & 0xffff)); |
WREG32(DMA_TILING_CONFIG, (gb_tiling_config & 0xffff)); |
WREG32(DMA_TILING_CONFIG2, (gb_tiling_config & 0xffff)); |
if (rdev->family == CHIP_RV730) { |
WREG32(UVD_UDEC_DB_TILING_CONFIG, (gb_tiling_config & 0xffff)); |
WREG32(UVD_UDEC_DBW_TILING_CONFIG, (gb_tiling_config & 0xffff)); |
WREG32(UVD_UDEC_TILING_CONFIG, (gb_tiling_config & 0xffff)); |
} |
WREG32(CGTS_SYS_TCC_DISABLE, 0); |
WREG32(CGTS_TCC_DISABLE, 0); |
731,7 → 1571,7 |
} |
if (rdev->flags & RADEON_IS_AGP) { |
size_bf = mc->gtt_start; |
size_af = 0xFFFFFFFF - mc->gtt_end; |
size_af = mc->mc_mask - mc->gtt_end; |
if (size_bf > size_af) { |
if (mc->mc_vram_size > size_bf) { |
dev_warn(rdev->dev, "limiting VRAM\n"); |
803,6 → 1643,80 |
return 0; |
} |
/** |
* rv770_copy_dma - copy pages using the DMA engine |
* |
* @rdev: radeon_device pointer |
* @src_offset: src GPU address |
* @dst_offset: dst GPU address |
* @num_gpu_pages: number of GPU pages to xfer |
* @fence: radeon fence object |
* |
* Copy GPU paging using the DMA engine (r7xx). |
* Used by the radeon ttm implementation to move pages if |
* registered as the asic copy callback. |
*/ |
int rv770_copy_dma(struct radeon_device *rdev, |
uint64_t src_offset, uint64_t dst_offset, |
unsigned num_gpu_pages, |
struct radeon_fence **fence) |
{ |
struct radeon_semaphore *sem = NULL; |
int ring_index = rdev->asic->copy.dma_ring_index; |
struct radeon_ring *ring = &rdev->ring[ring_index]; |
u32 size_in_dw, cur_size_in_dw; |
int i, num_loops; |
int r = 0; |
r = radeon_semaphore_create(rdev, &sem); |
if (r) { |
DRM_ERROR("radeon: moving bo (%d).\n", r); |
return r; |
} |
size_in_dw = (num_gpu_pages << RADEON_GPU_PAGE_SHIFT) / 4; |
num_loops = DIV_ROUND_UP(size_in_dw, 0xFFFF); |
r = radeon_ring_lock(rdev, ring, num_loops * 5 + 8); |
if (r) { |
DRM_ERROR("radeon: moving bo (%d).\n", r); |
radeon_semaphore_free(rdev, &sem, NULL); |
return r; |
} |
if (radeon_fence_need_sync(*fence, ring->idx)) { |
radeon_semaphore_sync_rings(rdev, sem, (*fence)->ring, |
ring->idx); |
radeon_fence_note_sync(*fence, ring->idx); |
} else { |
radeon_semaphore_free(rdev, &sem, NULL); |
} |
for (i = 0; i < num_loops; i++) { |
cur_size_in_dw = size_in_dw; |
if (cur_size_in_dw > 0xFFFF) |
cur_size_in_dw = 0xFFFF; |
size_in_dw -= cur_size_in_dw; |
radeon_ring_write(ring, DMA_PACKET(DMA_PACKET_COPY, 0, 0, cur_size_in_dw)); |
radeon_ring_write(ring, dst_offset & 0xfffffffc); |
radeon_ring_write(ring, src_offset & 0xfffffffc); |
radeon_ring_write(ring, upper_32_bits(dst_offset) & 0xff); |
radeon_ring_write(ring, upper_32_bits(src_offset) & 0xff); |
src_offset += cur_size_in_dw * 4; |
dst_offset += cur_size_in_dw * 4; |
} |
r = radeon_fence_emit(rdev, fence, ring->idx); |
if (r) { |
radeon_ring_unlock_undo(rdev, ring); |
return r; |
} |
radeon_ring_unlock_commit(rdev, ring); |
radeon_semaphore_free(rdev, &sem, *fence); |
return r; |
} |
static int rv770_startup(struct radeon_device *rdev) |
{ |
struct radeon_ring *ring; |
840,13 → 1754,6 |
dev_warn(rdev->dev, "failed blitter (%d) falling back to memcpy\n", r); |
} |
// r = r600_video_init(rdev); |
// if (r) { |
// r600_video_fini(rdev); |
// rdev->asic->copy = NULL; |
// dev_warn(rdev->dev, "failed video blitter (%d) falling back to memcpy\n", r); |
// } |
/* allocate wb buffer */ |
r = radeon_wb_init(rdev); |
if (r) |
864,7 → 1771,24 |
return r; |
} |
// r = rv770_uvd_resume(rdev); |
// if (!r) { |
// r = radeon_fence_driver_start_ring(rdev, |
// R600_RING_TYPE_UVD_INDEX); |
// if (r) |
// dev_err(rdev->dev, "UVD fences init error (%d).\n", r); |
// } |
// if (r) |
// rdev->ring[R600_RING_TYPE_UVD_INDEX].ring_size = 0; |
/* Enable IRQ */ |
if (!rdev->irq.installed) { |
r = radeon_irq_kms_init(rdev); |
if (r) |
return r; |
} |
r = r600_irq_init(rdev); |
if (r) { |
DRM_ERROR("radeon: IH init failed (%d).\n", r); |
898,6 → 1822,19 |
if (r) |
return r; |
// ring = &rdev->ring[R600_RING_TYPE_UVD_INDEX]; |
// if (ring->ring_size) { |
// r = radeon_ring_init(rdev, ring, ring->ring_size, |
// R600_WB_UVD_RPTR_OFFSET, |
// UVD_RBC_RB_RPTR, UVD_RBC_RB_WPTR, |
// 0, 0xfffff, RADEON_CP_PACKET2); |
// if (!r) |
// r = r600_uvd_init(rdev); |
// if (r) |
// DRM_ERROR("radeon: failed initializing UVD (%d).\n", r); |
// } |
r = radeon_ib_pool_init(rdev); |
if (r) { |
dev_err(rdev->dev, "IB initialization failed (%d).\n", r); |
946,6 → 1883,8 |
DRM_INFO("GPU not posted. posting now...\n"); |
atom_asic_init(rdev->mode_info.atom_context); |
} |
/* init golden registers */ |
rv770_init_golden_registers(rdev); |
/* Initialize scratch registers */ |
r600_scratch_init(rdev); |
/* Initialize surface registers */ |
970,10 → 1909,6 |
if (r) |
return r; |
r = radeon_irq_kms_init(rdev); |
if (r) |
return r; |
rdev->ring[RADEON_RING_TYPE_GFX_INDEX].ring_obj = NULL; |
r600_ring_init(rdev, &rdev->ring[RADEON_RING_TYPE_GFX_INDEX], 1024 * 1024); |
980,6 → 1915,13 |
rdev->ring[R600_RING_TYPE_DMA_INDEX].ring_obj = NULL; |
r600_ring_init(rdev, &rdev->ring[R600_RING_TYPE_DMA_INDEX], 64 * 1024); |
// r = radeon_uvd_init(rdev); |
// if (!r) { |
// rdev->ring[R600_RING_TYPE_UVD_INDEX].ring_obj = NULL; |
// r600_ring_init(rdev, &rdev->ring[R600_RING_TYPE_UVD_INDEX], |
// 4096); |
// } |
rdev->ih.ring_obj = NULL; |
r600_ih_ring_init(rdev, 64 * 1024); |
1002,8 → 1944,6 |
{ |
u32 link_width_cntl, lanes, speed_cntl, tmp; |
u16 link_cntl2; |
u32 mask; |
int ret; |
if (radeon_pcie_gen2 == 0) |
return; |
1018,20 → 1958,17 |
if (ASIC_IS_X2(rdev)) |
return; |
ret = drm_pcie_get_speed_cap_mask(rdev->ddev, &mask); |
if (ret != 0) |
if ((rdev->pdev->bus->max_bus_speed != PCIE_SPEED_5_0GT) && |
(rdev->pdev->bus->max_bus_speed != PCIE_SPEED_8_0GT)) |
return; |
if (!(mask & DRM_PCIE_SPEED_50)) |
return; |
DRM_INFO("enabling PCIE gen 2 link speeds, disable with radeon.pcie_gen2=0\n"); |
/* advertise upconfig capability */ |
link_width_cntl = RREG32_PCIE_P(PCIE_LC_LINK_WIDTH_CNTL); |
link_width_cntl = RREG32_PCIE_PORT(PCIE_LC_LINK_WIDTH_CNTL); |
link_width_cntl &= ~LC_UPCONFIGURE_DIS; |
WREG32_PCIE_P(PCIE_LC_LINK_WIDTH_CNTL, link_width_cntl); |
link_width_cntl = RREG32_PCIE_P(PCIE_LC_LINK_WIDTH_CNTL); |
WREG32_PCIE_PORT(PCIE_LC_LINK_WIDTH_CNTL, link_width_cntl); |
link_width_cntl = RREG32_PCIE_PORT(PCIE_LC_LINK_WIDTH_CNTL); |
if (link_width_cntl & LC_RENEGOTIATION_SUPPORT) { |
lanes = (link_width_cntl & LC_LINK_WIDTH_RD_MASK) >> LC_LINK_WIDTH_RD_SHIFT; |
link_width_cntl &= ~(LC_LINK_WIDTH_MASK | |
1038,13 → 1975,13 |
LC_RECONFIG_ARC_MISSING_ESCAPE); |
link_width_cntl |= lanes | LC_RECONFIG_NOW | |
LC_RENEGOTIATE_EN | LC_UPCONFIGURE_SUPPORT; |
WREG32_PCIE_P(PCIE_LC_LINK_WIDTH_CNTL, link_width_cntl); |
WREG32_PCIE_PORT(PCIE_LC_LINK_WIDTH_CNTL, link_width_cntl); |
} else { |
link_width_cntl |= LC_UPCONFIGURE_DIS; |
WREG32_PCIE_P(PCIE_LC_LINK_WIDTH_CNTL, link_width_cntl); |
WREG32_PCIE_PORT(PCIE_LC_LINK_WIDTH_CNTL, link_width_cntl); |
} |
speed_cntl = RREG32_PCIE_P(PCIE_LC_SPEED_CNTL); |
speed_cntl = RREG32_PCIE_PORT(PCIE_LC_SPEED_CNTL); |
if ((speed_cntl & LC_OTHER_SIDE_EVER_SENT_GEN2) && |
(speed_cntl & LC_OTHER_SIDE_SUPPORTS_GEN2)) { |
1057,29 → 1994,29 |
WREG16(0x4088, link_cntl2); |
WREG32(MM_CFGREGS_CNTL, 0); |
speed_cntl = RREG32_PCIE_P(PCIE_LC_SPEED_CNTL); |
speed_cntl = RREG32_PCIE_PORT(PCIE_LC_SPEED_CNTL); |
speed_cntl &= ~LC_TARGET_LINK_SPEED_OVERRIDE_EN; |
WREG32_PCIE_P(PCIE_LC_SPEED_CNTL, speed_cntl); |
WREG32_PCIE_PORT(PCIE_LC_SPEED_CNTL, speed_cntl); |
speed_cntl = RREG32_PCIE_P(PCIE_LC_SPEED_CNTL); |
speed_cntl = RREG32_PCIE_PORT(PCIE_LC_SPEED_CNTL); |
speed_cntl |= LC_CLR_FAILED_SPD_CHANGE_CNT; |
WREG32_PCIE_P(PCIE_LC_SPEED_CNTL, speed_cntl); |
WREG32_PCIE_PORT(PCIE_LC_SPEED_CNTL, speed_cntl); |
speed_cntl = RREG32_PCIE_P(PCIE_LC_SPEED_CNTL); |
speed_cntl = RREG32_PCIE_PORT(PCIE_LC_SPEED_CNTL); |
speed_cntl &= ~LC_CLR_FAILED_SPD_CHANGE_CNT; |
WREG32_PCIE_P(PCIE_LC_SPEED_CNTL, speed_cntl); |
WREG32_PCIE_PORT(PCIE_LC_SPEED_CNTL, speed_cntl); |
speed_cntl = RREG32_PCIE_P(PCIE_LC_SPEED_CNTL); |
speed_cntl = RREG32_PCIE_PORT(PCIE_LC_SPEED_CNTL); |
speed_cntl |= LC_GEN2_EN_STRAP; |
WREG32_PCIE_P(PCIE_LC_SPEED_CNTL, speed_cntl); |
WREG32_PCIE_PORT(PCIE_LC_SPEED_CNTL, speed_cntl); |
} else { |
link_width_cntl = RREG32_PCIE_P(PCIE_LC_LINK_WIDTH_CNTL); |
link_width_cntl = RREG32_PCIE_PORT(PCIE_LC_LINK_WIDTH_CNTL); |
/* XXX: only disable it if gen1 bridge vendor == 0x111d or 0x1106 */ |
if (1) |
link_width_cntl |= LC_UPCONFIGURE_DIS; |
else |
link_width_cntl &= ~LC_UPCONFIGURE_DIS; |
WREG32_PCIE_P(PCIE_LC_LINK_WIDTH_CNTL, link_width_cntl); |
WREG32_PCIE_PORT(PCIE_LC_LINK_WIDTH_CNTL, link_width_cntl); |
} |
} |
/drivers/video/drm/radeon/rv770d.h |
---|
38,6 → 38,30 |
#define R7XX_MAX_PIPES 8 |
#define R7XX_MAX_PIPES_MASK 0xff |
/* discrete uvd clocks */ |
#define CG_UPLL_FUNC_CNTL 0x718 |
# define UPLL_RESET_MASK 0x00000001 |
# define UPLL_SLEEP_MASK 0x00000002 |
# define UPLL_BYPASS_EN_MASK 0x00000004 |
# define UPLL_CTLREQ_MASK 0x00000008 |
# define UPLL_REF_DIV(x) ((x) << 16) |
# define UPLL_REF_DIV_MASK 0x003F0000 |
# define UPLL_CTLACK_MASK 0x40000000 |
# define UPLL_CTLACK2_MASK 0x80000000 |
#define CG_UPLL_FUNC_CNTL_2 0x71c |
# define UPLL_SW_HILEN(x) ((x) << 0) |
# define UPLL_SW_LOLEN(x) ((x) << 4) |
# define UPLL_SW_HILEN2(x) ((x) << 8) |
# define UPLL_SW_LOLEN2(x) ((x) << 12) |
# define UPLL_SW_MASK 0x0000FFFF |
# define VCLK_SRC_SEL(x) ((x) << 20) |
# define VCLK_SRC_SEL_MASK 0x01F00000 |
# define DCLK_SRC_SEL(x) ((x) << 25) |
# define DCLK_SRC_SEL_MASK 0x3E000000 |
#define CG_UPLL_FUNC_CNTL_3 0x720 |
# define UPLL_FB_DIV(x) ((x) << 0) |
# define UPLL_FB_DIV_MASK 0x01FFFFFF |
/* Registers */ |
#define CB_COLOR0_BASE 0x28040 |
#define CB_COLOR1_BASE 0x28044 |
112,6 → 136,11 |
#define DMA_TILING_CONFIG 0x3ec8 |
#define DMA_TILING_CONFIG2 0xd0b8 |
/* RV730 only */ |
#define UVD_UDEC_TILING_CONFIG 0xef40 |
#define UVD_UDEC_DB_TILING_CONFIG 0xef44 |
#define UVD_UDEC_DBW_TILING_CONFIG 0xef48 |
#define GC_USER_SHADER_PIPE_CONFIG 0x8954 |
#define INACTIVE_QD_PIPES(x) ((x) << 8) |
#define INACTIVE_QD_PIPES_MASK 0x0000FF00 |
128,6 → 157,10 |
#define GUI_ACTIVE (1<<31) |
#define GRBM_STATUS2 0x8014 |
#define CG_CLKPIN_CNTL 0x660 |
# define MUX_TCLK_TO_XCLK (1 << 8) |
# define XTALIN_DIVIDE (1 << 9) |
#define CG_MULT_THERMAL_STATUS 0x740 |
#define ASIC_T(x) ((x) << 16) |
#define ASIC_T_MASK 0x3FF0000 |
667,4 → 700,18 |
# define TARGET_LINK_SPEED_MASK (0xf << 0) |
# define SELECTABLE_DEEMPHASIS (1 << 6) |
/* UVD */ |
#define UVD_LMI_EXT40_ADDR 0xf498 |
#define UVD_VCPU_CHIP_ID 0xf4d4 |
#define UVD_VCPU_CACHE_OFFSET0 0xf4d8 |
#define UVD_VCPU_CACHE_SIZE0 0xf4dc |
#define UVD_VCPU_CACHE_OFFSET1 0xf4e0 |
#define UVD_VCPU_CACHE_SIZE1 0xf4e4 |
#define UVD_VCPU_CACHE_OFFSET2 0xf4e8 |
#define UVD_VCPU_CACHE_SIZE2 0xf4ec |
#define UVD_LMI_ADDR_EXT 0xf594 |
#define UVD_RBC_RB_RPTR 0xf690 |
#define UVD_RBC_RB_WPTR 0xf694 |
#endif |
/drivers/video/drm/radeon/si.c |
---|
38,6 → 38,7 |
#define SI_CE_UCODE_SIZE 2144 |
#define SI_RLC_UCODE_SIZE 2048 |
#define SI_MC_UCODE_SIZE 7769 |
#define OLAND_MC_UCODE_SIZE 7863 |
MODULE_FIRMWARE("radeon/TAHITI_pfp.bin"); |
MODULE_FIRMWARE("radeon/TAHITI_me.bin"); |
54,6 → 55,16 |
MODULE_FIRMWARE("radeon/VERDE_ce.bin"); |
MODULE_FIRMWARE("radeon/VERDE_mc.bin"); |
MODULE_FIRMWARE("radeon/VERDE_rlc.bin"); |
MODULE_FIRMWARE("radeon/OLAND_pfp.bin"); |
MODULE_FIRMWARE("radeon/OLAND_me.bin"); |
MODULE_FIRMWARE("radeon/OLAND_ce.bin"); |
MODULE_FIRMWARE("radeon/OLAND_mc.bin"); |
MODULE_FIRMWARE("radeon/OLAND_rlc.bin"); |
MODULE_FIRMWARE("radeon/HAINAN_pfp.bin"); |
MODULE_FIRMWARE("radeon/HAINAN_me.bin"); |
MODULE_FIRMWARE("radeon/HAINAN_ce.bin"); |
MODULE_FIRMWARE("radeon/HAINAN_mc.bin"); |
MODULE_FIRMWARE("radeon/HAINAN_rlc.bin"); |
extern int r600_ih_ring_alloc(struct radeon_device *rdev); |
extern void r600_ih_ring_fini(struct radeon_device *rdev); |
61,7 → 72,946 |
extern void evergreen_mc_stop(struct radeon_device *rdev, struct evergreen_mc_save *save); |
extern void evergreen_mc_resume(struct radeon_device *rdev, struct evergreen_mc_save *save); |
extern u32 evergreen_get_number_of_dram_channels(struct radeon_device *rdev); |
extern void evergreen_print_gpu_status_regs(struct radeon_device *rdev); |
extern bool evergreen_is_display_hung(struct radeon_device *rdev); |
static const u32 tahiti_golden_rlc_registers[] = |
{ |
0xc424, 0xffffffff, 0x00601005, |
0xc47c, 0xffffffff, 0x10104040, |
0xc488, 0xffffffff, 0x0100000a, |
0xc314, 0xffffffff, 0x00000800, |
0xc30c, 0xffffffff, 0x800000f4, |
0xf4a8, 0xffffffff, 0x00000000 |
}; |
static const u32 tahiti_golden_registers[] = |
{ |
0x9a10, 0x00010000, 0x00018208, |
0x9830, 0xffffffff, 0x00000000, |
0x9834, 0xf00fffff, 0x00000400, |
0x9838, 0x0002021c, 0x00020200, |
0xc78, 0x00000080, 0x00000000, |
0xd030, 0x000300c0, 0x00800040, |
0xd830, 0x000300c0, 0x00800040, |
0x5bb0, 0x000000f0, 0x00000070, |
0x5bc0, 0x00200000, 0x50100000, |
0x7030, 0x31000311, 0x00000011, |
0x277c, 0x00000003, 0x000007ff, |
0x240c, 0x000007ff, 0x00000000, |
0x8a14, 0xf000001f, 0x00000007, |
0x8b24, 0xffffffff, 0x00ffffff, |
0x8b10, 0x0000ff0f, 0x00000000, |
0x28a4c, 0x07ffffff, 0x4e000000, |
0x28350, 0x3f3f3fff, 0x2a00126a, |
0x30, 0x000000ff, 0x0040, |
0x34, 0x00000040, 0x00004040, |
0x9100, 0x07ffffff, 0x03000000, |
0x8e88, 0x01ff1f3f, 0x00000000, |
0x8e84, 0x01ff1f3f, 0x00000000, |
0x9060, 0x0000007f, 0x00000020, |
0x9508, 0x00010000, 0x00010000, |
0xac14, 0x00000200, 0x000002fb, |
0xac10, 0xffffffff, 0x0000543b, |
0xac0c, 0xffffffff, 0xa9210876, |
0x88d0, 0xffffffff, 0x000fff40, |
0x88d4, 0x0000001f, 0x00000010, |
0x1410, 0x20000000, 0x20fffed8, |
0x15c0, 0x000c0fc0, 0x000c0400 |
}; |
static const u32 tahiti_golden_registers2[] = |
{ |
0xc64, 0x00000001, 0x00000001 |
}; |
static const u32 pitcairn_golden_rlc_registers[] = |
{ |
0xc424, 0xffffffff, 0x00601004, |
0xc47c, 0xffffffff, 0x10102020, |
0xc488, 0xffffffff, 0x01000020, |
0xc314, 0xffffffff, 0x00000800, |
0xc30c, 0xffffffff, 0x800000a4 |
}; |
static const u32 pitcairn_golden_registers[] = |
{ |
0x9a10, 0x00010000, 0x00018208, |
0x9830, 0xffffffff, 0x00000000, |
0x9834, 0xf00fffff, 0x00000400, |
0x9838, 0x0002021c, 0x00020200, |
0xc78, 0x00000080, 0x00000000, |
0xd030, 0x000300c0, 0x00800040, |
0xd830, 0x000300c0, 0x00800040, |
0x5bb0, 0x000000f0, 0x00000070, |
0x5bc0, 0x00200000, 0x50100000, |
0x7030, 0x31000311, 0x00000011, |
0x2ae4, 0x00073ffe, 0x000022a2, |
0x240c, 0x000007ff, 0x00000000, |
0x8a14, 0xf000001f, 0x00000007, |
0x8b24, 0xffffffff, 0x00ffffff, |
0x8b10, 0x0000ff0f, 0x00000000, |
0x28a4c, 0x07ffffff, 0x4e000000, |
0x28350, 0x3f3f3fff, 0x2a00126a, |
0x30, 0x000000ff, 0x0040, |
0x34, 0x00000040, 0x00004040, |
0x9100, 0x07ffffff, 0x03000000, |
0x9060, 0x0000007f, 0x00000020, |
0x9508, 0x00010000, 0x00010000, |
0xac14, 0x000003ff, 0x000000f7, |
0xac10, 0xffffffff, 0x00000000, |
0xac0c, 0xffffffff, 0x32761054, |
0x88d4, 0x0000001f, 0x00000010, |
0x15c0, 0x000c0fc0, 0x000c0400 |
}; |
static const u32 verde_golden_rlc_registers[] = |
{ |
0xc424, 0xffffffff, 0x033f1005, |
0xc47c, 0xffffffff, 0x10808020, |
0xc488, 0xffffffff, 0x00800008, |
0xc314, 0xffffffff, 0x00001000, |
0xc30c, 0xffffffff, 0x80010014 |
}; |
static const u32 verde_golden_registers[] = |
{ |
0x9a10, 0x00010000, 0x00018208, |
0x9830, 0xffffffff, 0x00000000, |
0x9834, 0xf00fffff, 0x00000400, |
0x9838, 0x0002021c, 0x00020200, |
0xc78, 0x00000080, 0x00000000, |
0xd030, 0x000300c0, 0x00800040, |
0xd030, 0x000300c0, 0x00800040, |
0xd830, 0x000300c0, 0x00800040, |
0xd830, 0x000300c0, 0x00800040, |
0x5bb0, 0x000000f0, 0x00000070, |
0x5bc0, 0x00200000, 0x50100000, |
0x7030, 0x31000311, 0x00000011, |
0x2ae4, 0x00073ffe, 0x000022a2, |
0x2ae4, 0x00073ffe, 0x000022a2, |
0x2ae4, 0x00073ffe, 0x000022a2, |
0x240c, 0x000007ff, 0x00000000, |
0x240c, 0x000007ff, 0x00000000, |
0x240c, 0x000007ff, 0x00000000, |
0x8a14, 0xf000001f, 0x00000007, |
0x8a14, 0xf000001f, 0x00000007, |
0x8a14, 0xf000001f, 0x00000007, |
0x8b24, 0xffffffff, 0x00ffffff, |
0x8b10, 0x0000ff0f, 0x00000000, |
0x28a4c, 0x07ffffff, 0x4e000000, |
0x28350, 0x3f3f3fff, 0x0000124a, |
0x28350, 0x3f3f3fff, 0x0000124a, |
0x28350, 0x3f3f3fff, 0x0000124a, |
0x30, 0x000000ff, 0x0040, |
0x34, 0x00000040, 0x00004040, |
0x9100, 0x07ffffff, 0x03000000, |
0x9100, 0x07ffffff, 0x03000000, |
0x8e88, 0x01ff1f3f, 0x00000000, |
0x8e88, 0x01ff1f3f, 0x00000000, |
0x8e88, 0x01ff1f3f, 0x00000000, |
0x8e84, 0x01ff1f3f, 0x00000000, |
0x8e84, 0x01ff1f3f, 0x00000000, |
0x8e84, 0x01ff1f3f, 0x00000000, |
0x9060, 0x0000007f, 0x00000020, |
0x9508, 0x00010000, 0x00010000, |
0xac14, 0x000003ff, 0x00000003, |
0xac14, 0x000003ff, 0x00000003, |
0xac14, 0x000003ff, 0x00000003, |
0xac10, 0xffffffff, 0x00000000, |
0xac10, 0xffffffff, 0x00000000, |
0xac10, 0xffffffff, 0x00000000, |
0xac0c, 0xffffffff, 0x00001032, |
0xac0c, 0xffffffff, 0x00001032, |
0xac0c, 0xffffffff, 0x00001032, |
0x88d4, 0x0000001f, 0x00000010, |
0x88d4, 0x0000001f, 0x00000010, |
0x88d4, 0x0000001f, 0x00000010, |
0x15c0, 0x000c0fc0, 0x000c0400 |
}; |
static const u32 oland_golden_rlc_registers[] = |
{ |
0xc424, 0xffffffff, 0x00601005, |
0xc47c, 0xffffffff, 0x10104040, |
0xc488, 0xffffffff, 0x0100000a, |
0xc314, 0xffffffff, 0x00000800, |
0xc30c, 0xffffffff, 0x800000f4 |
}; |
static const u32 oland_golden_registers[] = |
{ |
0x9a10, 0x00010000, 0x00018208, |
0x9830, 0xffffffff, 0x00000000, |
0x9834, 0xf00fffff, 0x00000400, |
0x9838, 0x0002021c, 0x00020200, |
0xc78, 0x00000080, 0x00000000, |
0xd030, 0x000300c0, 0x00800040, |
0xd830, 0x000300c0, 0x00800040, |
0x5bb0, 0x000000f0, 0x00000070, |
0x5bc0, 0x00200000, 0x50100000, |
0x7030, 0x31000311, 0x00000011, |
0x2ae4, 0x00073ffe, 0x000022a2, |
0x240c, 0x000007ff, 0x00000000, |
0x8a14, 0xf000001f, 0x00000007, |
0x8b24, 0xffffffff, 0x00ffffff, |
0x8b10, 0x0000ff0f, 0x00000000, |
0x28a4c, 0x07ffffff, 0x4e000000, |
0x28350, 0x3f3f3fff, 0x00000082, |
0x30, 0x000000ff, 0x0040, |
0x34, 0x00000040, 0x00004040, |
0x9100, 0x07ffffff, 0x03000000, |
0x9060, 0x0000007f, 0x00000020, |
0x9508, 0x00010000, 0x00010000, |
0xac14, 0x000003ff, 0x000000f3, |
0xac10, 0xffffffff, 0x00000000, |
0xac0c, 0xffffffff, 0x00003210, |
0x88d4, 0x0000001f, 0x00000010, |
0x15c0, 0x000c0fc0, 0x000c0400 |
}; |
static const u32 hainan_golden_registers[] = |
{ |
0x9a10, 0x00010000, 0x00018208, |
0x9830, 0xffffffff, 0x00000000, |
0x9834, 0xf00fffff, 0x00000400, |
0x9838, 0x0002021c, 0x00020200, |
0xd0c0, 0xff000fff, 0x00000100, |
0xd030, 0x000300c0, 0x00800040, |
0xd8c0, 0xff000fff, 0x00000100, |
0xd830, 0x000300c0, 0x00800040, |
0x2ae4, 0x00073ffe, 0x000022a2, |
0x240c, 0x000007ff, 0x00000000, |
0x8a14, 0xf000001f, 0x00000007, |
0x8b24, 0xffffffff, 0x00ffffff, |
0x8b10, 0x0000ff0f, 0x00000000, |
0x28a4c, 0x07ffffff, 0x4e000000, |
0x28350, 0x3f3f3fff, 0x00000000, |
0x30, 0x000000ff, 0x0040, |
0x34, 0x00000040, 0x00004040, |
0x9100, 0x03e00000, 0x03600000, |
0x9060, 0x0000007f, 0x00000020, |
0x9508, 0x00010000, 0x00010000, |
0xac14, 0x000003ff, 0x000000f1, |
0xac10, 0xffffffff, 0x00000000, |
0xac0c, 0xffffffff, 0x00003210, |
0x88d4, 0x0000001f, 0x00000010, |
0x15c0, 0x000c0fc0, 0x000c0400 |
}; |
static const u32 hainan_golden_registers2[] = |
{ |
0x98f8, 0xffffffff, 0x02010001 |
}; |
static const u32 tahiti_mgcg_cgcg_init[] = |
{ |
0xc400, 0xffffffff, 0xfffffffc, |
0x802c, 0xffffffff, 0xe0000000, |
0x9a60, 0xffffffff, 0x00000100, |
0x92a4, 0xffffffff, 0x00000100, |
0xc164, 0xffffffff, 0x00000100, |
0x9774, 0xffffffff, 0x00000100, |
0x8984, 0xffffffff, 0x06000100, |
0x8a18, 0xffffffff, 0x00000100, |
0x92a0, 0xffffffff, 0x00000100, |
0xc380, 0xffffffff, 0x00000100, |
0x8b28, 0xffffffff, 0x00000100, |
0x9144, 0xffffffff, 0x00000100, |
0x8d88, 0xffffffff, 0x00000100, |
0x8d8c, 0xffffffff, 0x00000100, |
0x9030, 0xffffffff, 0x00000100, |
0x9034, 0xffffffff, 0x00000100, |
0x9038, 0xffffffff, 0x00000100, |
0x903c, 0xffffffff, 0x00000100, |
0xad80, 0xffffffff, 0x00000100, |
0xac54, 0xffffffff, 0x00000100, |
0x897c, 0xffffffff, 0x06000100, |
0x9868, 0xffffffff, 0x00000100, |
0x9510, 0xffffffff, 0x00000100, |
0xaf04, 0xffffffff, 0x00000100, |
0xae04, 0xffffffff, 0x00000100, |
0x949c, 0xffffffff, 0x00000100, |
0x802c, 0xffffffff, 0xe0000000, |
0x9160, 0xffffffff, 0x00010000, |
0x9164, 0xffffffff, 0x00030002, |
0x9168, 0xffffffff, 0x00040007, |
0x916c, 0xffffffff, 0x00060005, |
0x9170, 0xffffffff, 0x00090008, |
0x9174, 0xffffffff, 0x00020001, |
0x9178, 0xffffffff, 0x00040003, |
0x917c, 0xffffffff, 0x00000007, |
0x9180, 0xffffffff, 0x00060005, |
0x9184, 0xffffffff, 0x00090008, |
0x9188, 0xffffffff, 0x00030002, |
0x918c, 0xffffffff, 0x00050004, |
0x9190, 0xffffffff, 0x00000008, |
0x9194, 0xffffffff, 0x00070006, |
0x9198, 0xffffffff, 0x000a0009, |
0x919c, 0xffffffff, 0x00040003, |
0x91a0, 0xffffffff, 0x00060005, |
0x91a4, 0xffffffff, 0x00000009, |
0x91a8, 0xffffffff, 0x00080007, |
0x91ac, 0xffffffff, 0x000b000a, |
0x91b0, 0xffffffff, 0x00050004, |
0x91b4, 0xffffffff, 0x00070006, |
0x91b8, 0xffffffff, 0x0008000b, |
0x91bc, 0xffffffff, 0x000a0009, |
0x91c0, 0xffffffff, 0x000d000c, |
0x91c4, 0xffffffff, 0x00060005, |
0x91c8, 0xffffffff, 0x00080007, |
0x91cc, 0xffffffff, 0x0000000b, |
0x91d0, 0xffffffff, 0x000a0009, |
0x91d4, 0xffffffff, 0x000d000c, |
0x91d8, 0xffffffff, 0x00070006, |
0x91dc, 0xffffffff, 0x00090008, |
0x91e0, 0xffffffff, 0x0000000c, |
0x91e4, 0xffffffff, 0x000b000a, |
0x91e8, 0xffffffff, 0x000e000d, |
0x91ec, 0xffffffff, 0x00080007, |
0x91f0, 0xffffffff, 0x000a0009, |
0x91f4, 0xffffffff, 0x0000000d, |
0x91f8, 0xffffffff, 0x000c000b, |
0x91fc, 0xffffffff, 0x000f000e, |
0x9200, 0xffffffff, 0x00090008, |
0x9204, 0xffffffff, 0x000b000a, |
0x9208, 0xffffffff, 0x000c000f, |
0x920c, 0xffffffff, 0x000e000d, |
0x9210, 0xffffffff, 0x00110010, |
0x9214, 0xffffffff, 0x000a0009, |
0x9218, 0xffffffff, 0x000c000b, |
0x921c, 0xffffffff, 0x0000000f, |
0x9220, 0xffffffff, 0x000e000d, |
0x9224, 0xffffffff, 0x00110010, |
0x9228, 0xffffffff, 0x000b000a, |
0x922c, 0xffffffff, 0x000d000c, |
0x9230, 0xffffffff, 0x00000010, |
0x9234, 0xffffffff, 0x000f000e, |
0x9238, 0xffffffff, 0x00120011, |
0x923c, 0xffffffff, 0x000c000b, |
0x9240, 0xffffffff, 0x000e000d, |
0x9244, 0xffffffff, 0x00000011, |
0x9248, 0xffffffff, 0x0010000f, |
0x924c, 0xffffffff, 0x00130012, |
0x9250, 0xffffffff, 0x000d000c, |
0x9254, 0xffffffff, 0x000f000e, |
0x9258, 0xffffffff, 0x00100013, |
0x925c, 0xffffffff, 0x00120011, |
0x9260, 0xffffffff, 0x00150014, |
0x9264, 0xffffffff, 0x000e000d, |
0x9268, 0xffffffff, 0x0010000f, |
0x926c, 0xffffffff, 0x00000013, |
0x9270, 0xffffffff, 0x00120011, |
0x9274, 0xffffffff, 0x00150014, |
0x9278, 0xffffffff, 0x000f000e, |
0x927c, 0xffffffff, 0x00110010, |
0x9280, 0xffffffff, 0x00000014, |
0x9284, 0xffffffff, 0x00130012, |
0x9288, 0xffffffff, 0x00160015, |
0x928c, 0xffffffff, 0x0010000f, |
0x9290, 0xffffffff, 0x00120011, |
0x9294, 0xffffffff, 0x00000015, |
0x9298, 0xffffffff, 0x00140013, |
0x929c, 0xffffffff, 0x00170016, |
0x9150, 0xffffffff, 0x96940200, |
0x8708, 0xffffffff, 0x00900100, |
0xc478, 0xffffffff, 0x00000080, |
0xc404, 0xffffffff, 0x0020003f, |
0x30, 0xffffffff, 0x0000001c, |
0x34, 0x000f0000, 0x000f0000, |
0x160c, 0xffffffff, 0x00000100, |
0x1024, 0xffffffff, 0x00000100, |
0x102c, 0x00000101, 0x00000000, |
0x20a8, 0xffffffff, 0x00000104, |
0x264c, 0x000c0000, 0x000c0000, |
0x2648, 0x000c0000, 0x000c0000, |
0x55e4, 0xff000fff, 0x00000100, |
0x55e8, 0x00000001, 0x00000001, |
0x2f50, 0x00000001, 0x00000001, |
0x30cc, 0xc0000fff, 0x00000104, |
0xc1e4, 0x00000001, 0x00000001, |
0xd0c0, 0xfffffff0, 0x00000100, |
0xd8c0, 0xfffffff0, 0x00000100 |
}; |
static const u32 pitcairn_mgcg_cgcg_init[] = |
{ |
0xc400, 0xffffffff, 0xfffffffc, |
0x802c, 0xffffffff, 0xe0000000, |
0x9a60, 0xffffffff, 0x00000100, |
0x92a4, 0xffffffff, 0x00000100, |
0xc164, 0xffffffff, 0x00000100, |
0x9774, 0xffffffff, 0x00000100, |
0x8984, 0xffffffff, 0x06000100, |
0x8a18, 0xffffffff, 0x00000100, |
0x92a0, 0xffffffff, 0x00000100, |
0xc380, 0xffffffff, 0x00000100, |
0x8b28, 0xffffffff, 0x00000100, |
0x9144, 0xffffffff, 0x00000100, |
0x8d88, 0xffffffff, 0x00000100, |
0x8d8c, 0xffffffff, 0x00000100, |
0x9030, 0xffffffff, 0x00000100, |
0x9034, 0xffffffff, 0x00000100, |
0x9038, 0xffffffff, 0x00000100, |
0x903c, 0xffffffff, 0x00000100, |
0xad80, 0xffffffff, 0x00000100, |
0xac54, 0xffffffff, 0x00000100, |
0x897c, 0xffffffff, 0x06000100, |
0x9868, 0xffffffff, 0x00000100, |
0x9510, 0xffffffff, 0x00000100, |
0xaf04, 0xffffffff, 0x00000100, |
0xae04, 0xffffffff, 0x00000100, |
0x949c, 0xffffffff, 0x00000100, |
0x802c, 0xffffffff, 0xe0000000, |
0x9160, 0xffffffff, 0x00010000, |
0x9164, 0xffffffff, 0x00030002, |
0x9168, 0xffffffff, 0x00040007, |
0x916c, 0xffffffff, 0x00060005, |
0x9170, 0xffffffff, 0x00090008, |
0x9174, 0xffffffff, 0x00020001, |
0x9178, 0xffffffff, 0x00040003, |
0x917c, 0xffffffff, 0x00000007, |
0x9180, 0xffffffff, 0x00060005, |
0x9184, 0xffffffff, 0x00090008, |
0x9188, 0xffffffff, 0x00030002, |
0x918c, 0xffffffff, 0x00050004, |
0x9190, 0xffffffff, 0x00000008, |
0x9194, 0xffffffff, 0x00070006, |
0x9198, 0xffffffff, 0x000a0009, |
0x919c, 0xffffffff, 0x00040003, |
0x91a0, 0xffffffff, 0x00060005, |
0x91a4, 0xffffffff, 0x00000009, |
0x91a8, 0xffffffff, 0x00080007, |
0x91ac, 0xffffffff, 0x000b000a, |
0x91b0, 0xffffffff, 0x00050004, |
0x91b4, 0xffffffff, 0x00070006, |
0x91b8, 0xffffffff, 0x0008000b, |
0x91bc, 0xffffffff, 0x000a0009, |
0x91c0, 0xffffffff, 0x000d000c, |
0x9200, 0xffffffff, 0x00090008, |
0x9204, 0xffffffff, 0x000b000a, |
0x9208, 0xffffffff, 0x000c000f, |
0x920c, 0xffffffff, 0x000e000d, |
0x9210, 0xffffffff, 0x00110010, |
0x9214, 0xffffffff, 0x000a0009, |
0x9218, 0xffffffff, 0x000c000b, |
0x921c, 0xffffffff, 0x0000000f, |
0x9220, 0xffffffff, 0x000e000d, |
0x9224, 0xffffffff, 0x00110010, |
0x9228, 0xffffffff, 0x000b000a, |
0x922c, 0xffffffff, 0x000d000c, |
0x9230, 0xffffffff, 0x00000010, |
0x9234, 0xffffffff, 0x000f000e, |
0x9238, 0xffffffff, 0x00120011, |
0x923c, 0xffffffff, 0x000c000b, |
0x9240, 0xffffffff, 0x000e000d, |
0x9244, 0xffffffff, 0x00000011, |
0x9248, 0xffffffff, 0x0010000f, |
0x924c, 0xffffffff, 0x00130012, |
0x9250, 0xffffffff, 0x000d000c, |
0x9254, 0xffffffff, 0x000f000e, |
0x9258, 0xffffffff, 0x00100013, |
0x925c, 0xffffffff, 0x00120011, |
0x9260, 0xffffffff, 0x00150014, |
0x9150, 0xffffffff, 0x96940200, |
0x8708, 0xffffffff, 0x00900100, |
0xc478, 0xffffffff, 0x00000080, |
0xc404, 0xffffffff, 0x0020003f, |
0x30, 0xffffffff, 0x0000001c, |
0x34, 0x000f0000, 0x000f0000, |
0x160c, 0xffffffff, 0x00000100, |
0x1024, 0xffffffff, 0x00000100, |
0x102c, 0x00000101, 0x00000000, |
0x20a8, 0xffffffff, 0x00000104, |
0x55e4, 0xff000fff, 0x00000100, |
0x55e8, 0x00000001, 0x00000001, |
0x2f50, 0x00000001, 0x00000001, |
0x30cc, 0xc0000fff, 0x00000104, |
0xc1e4, 0x00000001, 0x00000001, |
0xd0c0, 0xfffffff0, 0x00000100, |
0xd8c0, 0xfffffff0, 0x00000100 |
}; |
static const u32 verde_mgcg_cgcg_init[] = |
{ |
0xc400, 0xffffffff, 0xfffffffc, |
0x802c, 0xffffffff, 0xe0000000, |
0x9a60, 0xffffffff, 0x00000100, |
0x92a4, 0xffffffff, 0x00000100, |
0xc164, 0xffffffff, 0x00000100, |
0x9774, 0xffffffff, 0x00000100, |
0x8984, 0xffffffff, 0x06000100, |
0x8a18, 0xffffffff, 0x00000100, |
0x92a0, 0xffffffff, 0x00000100, |
0xc380, 0xffffffff, 0x00000100, |
0x8b28, 0xffffffff, 0x00000100, |
0x9144, 0xffffffff, 0x00000100, |
0x8d88, 0xffffffff, 0x00000100, |
0x8d8c, 0xffffffff, 0x00000100, |
0x9030, 0xffffffff, 0x00000100, |
0x9034, 0xffffffff, 0x00000100, |
0x9038, 0xffffffff, 0x00000100, |
0x903c, 0xffffffff, 0x00000100, |
0xad80, 0xffffffff, 0x00000100, |
0xac54, 0xffffffff, 0x00000100, |
0x897c, 0xffffffff, 0x06000100, |
0x9868, 0xffffffff, 0x00000100, |
0x9510, 0xffffffff, 0x00000100, |
0xaf04, 0xffffffff, 0x00000100, |
0xae04, 0xffffffff, 0x00000100, |
0x949c, 0xffffffff, 0x00000100, |
0x802c, 0xffffffff, 0xe0000000, |
0x9160, 0xffffffff, 0x00010000, |
0x9164, 0xffffffff, 0x00030002, |
0x9168, 0xffffffff, 0x00040007, |
0x916c, 0xffffffff, 0x00060005, |
0x9170, 0xffffffff, 0x00090008, |
0x9174, 0xffffffff, 0x00020001, |
0x9178, 0xffffffff, 0x00040003, |
0x917c, 0xffffffff, 0x00000007, |
0x9180, 0xffffffff, 0x00060005, |
0x9184, 0xffffffff, 0x00090008, |
0x9188, 0xffffffff, 0x00030002, |
0x918c, 0xffffffff, 0x00050004, |
0x9190, 0xffffffff, 0x00000008, |
0x9194, 0xffffffff, 0x00070006, |
0x9198, 0xffffffff, 0x000a0009, |
0x919c, 0xffffffff, 0x00040003, |
0x91a0, 0xffffffff, 0x00060005, |
0x91a4, 0xffffffff, 0x00000009, |
0x91a8, 0xffffffff, 0x00080007, |
0x91ac, 0xffffffff, 0x000b000a, |
0x91b0, 0xffffffff, 0x00050004, |
0x91b4, 0xffffffff, 0x00070006, |
0x91b8, 0xffffffff, 0x0008000b, |
0x91bc, 0xffffffff, 0x000a0009, |
0x91c0, 0xffffffff, 0x000d000c, |
0x9200, 0xffffffff, 0x00090008, |
0x9204, 0xffffffff, 0x000b000a, |
0x9208, 0xffffffff, 0x000c000f, |
0x920c, 0xffffffff, 0x000e000d, |
0x9210, 0xffffffff, 0x00110010, |
0x9214, 0xffffffff, 0x000a0009, |
0x9218, 0xffffffff, 0x000c000b, |
0x921c, 0xffffffff, 0x0000000f, |
0x9220, 0xffffffff, 0x000e000d, |
0x9224, 0xffffffff, 0x00110010, |
0x9228, 0xffffffff, 0x000b000a, |
0x922c, 0xffffffff, 0x000d000c, |
0x9230, 0xffffffff, 0x00000010, |
0x9234, 0xffffffff, 0x000f000e, |
0x9238, 0xffffffff, 0x00120011, |
0x923c, 0xffffffff, 0x000c000b, |
0x9240, 0xffffffff, 0x000e000d, |
0x9244, 0xffffffff, 0x00000011, |
0x9248, 0xffffffff, 0x0010000f, |
0x924c, 0xffffffff, 0x00130012, |
0x9250, 0xffffffff, 0x000d000c, |
0x9254, 0xffffffff, 0x000f000e, |
0x9258, 0xffffffff, 0x00100013, |
0x925c, 0xffffffff, 0x00120011, |
0x9260, 0xffffffff, 0x00150014, |
0x9150, 0xffffffff, 0x96940200, |
0x8708, 0xffffffff, 0x00900100, |
0xc478, 0xffffffff, 0x00000080, |
0xc404, 0xffffffff, 0x0020003f, |
0x30, 0xffffffff, 0x0000001c, |
0x34, 0x000f0000, 0x000f0000, |
0x160c, 0xffffffff, 0x00000100, |
0x1024, 0xffffffff, 0x00000100, |
0x102c, 0x00000101, 0x00000000, |
0x20a8, 0xffffffff, 0x00000104, |
0x264c, 0x000c0000, 0x000c0000, |
0x2648, 0x000c0000, 0x000c0000, |
0x55e4, 0xff000fff, 0x00000100, |
0x55e8, 0x00000001, 0x00000001, |
0x2f50, 0x00000001, 0x00000001, |
0x30cc, 0xc0000fff, 0x00000104, |
0xc1e4, 0x00000001, 0x00000001, |
0xd0c0, 0xfffffff0, 0x00000100, |
0xd8c0, 0xfffffff0, 0x00000100 |
}; |
static const u32 oland_mgcg_cgcg_init[] = |
{ |
0xc400, 0xffffffff, 0xfffffffc, |
0x802c, 0xffffffff, 0xe0000000, |
0x9a60, 0xffffffff, 0x00000100, |
0x92a4, 0xffffffff, 0x00000100, |
0xc164, 0xffffffff, 0x00000100, |
0x9774, 0xffffffff, 0x00000100, |
0x8984, 0xffffffff, 0x06000100, |
0x8a18, 0xffffffff, 0x00000100, |
0x92a0, 0xffffffff, 0x00000100, |
0xc380, 0xffffffff, 0x00000100, |
0x8b28, 0xffffffff, 0x00000100, |
0x9144, 0xffffffff, 0x00000100, |
0x8d88, 0xffffffff, 0x00000100, |
0x8d8c, 0xffffffff, 0x00000100, |
0x9030, 0xffffffff, 0x00000100, |
0x9034, 0xffffffff, 0x00000100, |
0x9038, 0xffffffff, 0x00000100, |
0x903c, 0xffffffff, 0x00000100, |
0xad80, 0xffffffff, 0x00000100, |
0xac54, 0xffffffff, 0x00000100, |
0x897c, 0xffffffff, 0x06000100, |
0x9868, 0xffffffff, 0x00000100, |
0x9510, 0xffffffff, 0x00000100, |
0xaf04, 0xffffffff, 0x00000100, |
0xae04, 0xffffffff, 0x00000100, |
0x949c, 0xffffffff, 0x00000100, |
0x802c, 0xffffffff, 0xe0000000, |
0x9160, 0xffffffff, 0x00010000, |
0x9164, 0xffffffff, 0x00030002, |
0x9168, 0xffffffff, 0x00040007, |
0x916c, 0xffffffff, 0x00060005, |
0x9170, 0xffffffff, 0x00090008, |
0x9174, 0xffffffff, 0x00020001, |
0x9178, 0xffffffff, 0x00040003, |
0x917c, 0xffffffff, 0x00000007, |
0x9180, 0xffffffff, 0x00060005, |
0x9184, 0xffffffff, 0x00090008, |
0x9188, 0xffffffff, 0x00030002, |
0x918c, 0xffffffff, 0x00050004, |
0x9190, 0xffffffff, 0x00000008, |
0x9194, 0xffffffff, 0x00070006, |
0x9198, 0xffffffff, 0x000a0009, |
0x919c, 0xffffffff, 0x00040003, |
0x91a0, 0xffffffff, 0x00060005, |
0x91a4, 0xffffffff, 0x00000009, |
0x91a8, 0xffffffff, 0x00080007, |
0x91ac, 0xffffffff, 0x000b000a, |
0x91b0, 0xffffffff, 0x00050004, |
0x91b4, 0xffffffff, 0x00070006, |
0x91b8, 0xffffffff, 0x0008000b, |
0x91bc, 0xffffffff, 0x000a0009, |
0x91c0, 0xffffffff, 0x000d000c, |
0x91c4, 0xffffffff, 0x00060005, |
0x91c8, 0xffffffff, 0x00080007, |
0x91cc, 0xffffffff, 0x0000000b, |
0x91d0, 0xffffffff, 0x000a0009, |
0x91d4, 0xffffffff, 0x000d000c, |
0x9150, 0xffffffff, 0x96940200, |
0x8708, 0xffffffff, 0x00900100, |
0xc478, 0xffffffff, 0x00000080, |
0xc404, 0xffffffff, 0x0020003f, |
0x30, 0xffffffff, 0x0000001c, |
0x34, 0x000f0000, 0x000f0000, |
0x160c, 0xffffffff, 0x00000100, |
0x1024, 0xffffffff, 0x00000100, |
0x102c, 0x00000101, 0x00000000, |
0x20a8, 0xffffffff, 0x00000104, |
0x264c, 0x000c0000, 0x000c0000, |
0x2648, 0x000c0000, 0x000c0000, |
0x55e4, 0xff000fff, 0x00000100, |
0x55e8, 0x00000001, 0x00000001, |
0x2f50, 0x00000001, 0x00000001, |
0x30cc, 0xc0000fff, 0x00000104, |
0xc1e4, 0x00000001, 0x00000001, |
0xd0c0, 0xfffffff0, 0x00000100, |
0xd8c0, 0xfffffff0, 0x00000100 |
}; |
static const u32 hainan_mgcg_cgcg_init[] = |
{ |
0xc400, 0xffffffff, 0xfffffffc, |
0x802c, 0xffffffff, 0xe0000000, |
0x9a60, 0xffffffff, 0x00000100, |
0x92a4, 0xffffffff, 0x00000100, |
0xc164, 0xffffffff, 0x00000100, |
0x9774, 0xffffffff, 0x00000100, |
0x8984, 0xffffffff, 0x06000100, |
0x8a18, 0xffffffff, 0x00000100, |
0x92a0, 0xffffffff, 0x00000100, |
0xc380, 0xffffffff, 0x00000100, |
0x8b28, 0xffffffff, 0x00000100, |
0x9144, 0xffffffff, 0x00000100, |
0x8d88, 0xffffffff, 0x00000100, |
0x8d8c, 0xffffffff, 0x00000100, |
0x9030, 0xffffffff, 0x00000100, |
0x9034, 0xffffffff, 0x00000100, |
0x9038, 0xffffffff, 0x00000100, |
0x903c, 0xffffffff, 0x00000100, |
0xad80, 0xffffffff, 0x00000100, |
0xac54, 0xffffffff, 0x00000100, |
0x897c, 0xffffffff, 0x06000100, |
0x9868, 0xffffffff, 0x00000100, |
0x9510, 0xffffffff, 0x00000100, |
0xaf04, 0xffffffff, 0x00000100, |
0xae04, 0xffffffff, 0x00000100, |
0x949c, 0xffffffff, 0x00000100, |
0x802c, 0xffffffff, 0xe0000000, |
0x9160, 0xffffffff, 0x00010000, |
0x9164, 0xffffffff, 0x00030002, |
0x9168, 0xffffffff, 0x00040007, |
0x916c, 0xffffffff, 0x00060005, |
0x9170, 0xffffffff, 0x00090008, |
0x9174, 0xffffffff, 0x00020001, |
0x9178, 0xffffffff, 0x00040003, |
0x917c, 0xffffffff, 0x00000007, |
0x9180, 0xffffffff, 0x00060005, |
0x9184, 0xffffffff, 0x00090008, |
0x9188, 0xffffffff, 0x00030002, |
0x918c, 0xffffffff, 0x00050004, |
0x9190, 0xffffffff, 0x00000008, |
0x9194, 0xffffffff, 0x00070006, |
0x9198, 0xffffffff, 0x000a0009, |
0x919c, 0xffffffff, 0x00040003, |
0x91a0, 0xffffffff, 0x00060005, |
0x91a4, 0xffffffff, 0x00000009, |
0x91a8, 0xffffffff, 0x00080007, |
0x91ac, 0xffffffff, 0x000b000a, |
0x91b0, 0xffffffff, 0x00050004, |
0x91b4, 0xffffffff, 0x00070006, |
0x91b8, 0xffffffff, 0x0008000b, |
0x91bc, 0xffffffff, 0x000a0009, |
0x91c0, 0xffffffff, 0x000d000c, |
0x91c4, 0xffffffff, 0x00060005, |
0x91c8, 0xffffffff, 0x00080007, |
0x91cc, 0xffffffff, 0x0000000b, |
0x91d0, 0xffffffff, 0x000a0009, |
0x91d4, 0xffffffff, 0x000d000c, |
0x9150, 0xffffffff, 0x96940200, |
0x8708, 0xffffffff, 0x00900100, |
0xc478, 0xffffffff, 0x00000080, |
0xc404, 0xffffffff, 0x0020003f, |
0x30, 0xffffffff, 0x0000001c, |
0x34, 0x000f0000, 0x000f0000, |
0x160c, 0xffffffff, 0x00000100, |
0x1024, 0xffffffff, 0x00000100, |
0x20a8, 0xffffffff, 0x00000104, |
0x264c, 0x000c0000, 0x000c0000, |
0x2648, 0x000c0000, 0x000c0000, |
0x2f50, 0x00000001, 0x00000001, |
0x30cc, 0xc0000fff, 0x00000104, |
0xc1e4, 0x00000001, 0x00000001, |
0xd0c0, 0xfffffff0, 0x00000100, |
0xd8c0, 0xfffffff0, 0x00000100 |
}; |
static u32 verde_pg_init[] = |
{ |
0x353c, 0xffffffff, 0x40000, |
0x3538, 0xffffffff, 0x200010ff, |
0x353c, 0xffffffff, 0x0, |
0x353c, 0xffffffff, 0x0, |
0x353c, 0xffffffff, 0x0, |
0x353c, 0xffffffff, 0x0, |
0x353c, 0xffffffff, 0x0, |
0x353c, 0xffffffff, 0x7007, |
0x3538, 0xffffffff, 0x300010ff, |
0x353c, 0xffffffff, 0x0, |
0x353c, 0xffffffff, 0x0, |
0x353c, 0xffffffff, 0x0, |
0x353c, 0xffffffff, 0x0, |
0x353c, 0xffffffff, 0x0, |
0x353c, 0xffffffff, 0x400000, |
0x3538, 0xffffffff, 0x100010ff, |
0x353c, 0xffffffff, 0x0, |
0x353c, 0xffffffff, 0x0, |
0x353c, 0xffffffff, 0x0, |
0x353c, 0xffffffff, 0x0, |
0x353c, 0xffffffff, 0x0, |
0x353c, 0xffffffff, 0x120200, |
0x3538, 0xffffffff, 0x500010ff, |
0x353c, 0xffffffff, 0x0, |
0x353c, 0xffffffff, 0x0, |
0x353c, 0xffffffff, 0x0, |
0x353c, 0xffffffff, 0x0, |
0x353c, 0xffffffff, 0x0, |
0x353c, 0xffffffff, 0x1e1e16, |
0x3538, 0xffffffff, 0x600010ff, |
0x353c, 0xffffffff, 0x0, |
0x353c, 0xffffffff, 0x0, |
0x353c, 0xffffffff, 0x0, |
0x353c, 0xffffffff, 0x0, |
0x353c, 0xffffffff, 0x0, |
0x353c, 0xffffffff, 0x171f1e, |
0x3538, 0xffffffff, 0x700010ff, |
0x353c, 0xffffffff, 0x0, |
0x353c, 0xffffffff, 0x0, |
0x353c, 0xffffffff, 0x0, |
0x353c, 0xffffffff, 0x0, |
0x353c, 0xffffffff, 0x0, |
0x353c, 0xffffffff, 0x0, |
0x3538, 0xffffffff, 0x9ff, |
0x3500, 0xffffffff, 0x0, |
0x3504, 0xffffffff, 0x10000800, |
0x3504, 0xffffffff, 0xf, |
0x3504, 0xffffffff, 0xf, |
0x3500, 0xffffffff, 0x4, |
0x3504, 0xffffffff, 0x1000051e, |
0x3504, 0xffffffff, 0xffff, |
0x3504, 0xffffffff, 0xffff, |
0x3500, 0xffffffff, 0x8, |
0x3504, 0xffffffff, 0x80500, |
0x3500, 0xffffffff, 0x12, |
0x3504, 0xffffffff, 0x9050c, |
0x3500, 0xffffffff, 0x1d, |
0x3504, 0xffffffff, 0xb052c, |
0x3500, 0xffffffff, 0x2a, |
0x3504, 0xffffffff, 0x1053e, |
0x3500, 0xffffffff, 0x2d, |
0x3504, 0xffffffff, 0x10546, |
0x3500, 0xffffffff, 0x30, |
0x3504, 0xffffffff, 0xa054e, |
0x3500, 0xffffffff, 0x3c, |
0x3504, 0xffffffff, 0x1055f, |
0x3500, 0xffffffff, 0x3f, |
0x3504, 0xffffffff, 0x10567, |
0x3500, 0xffffffff, 0x42, |
0x3504, 0xffffffff, 0x1056f, |
0x3500, 0xffffffff, 0x45, |
0x3504, 0xffffffff, 0x10572, |
0x3500, 0xffffffff, 0x48, |
0x3504, 0xffffffff, 0x20575, |
0x3500, 0xffffffff, 0x4c, |
0x3504, 0xffffffff, 0x190801, |
0x3500, 0xffffffff, 0x67, |
0x3504, 0xffffffff, 0x1082a, |
0x3500, 0xffffffff, 0x6a, |
0x3504, 0xffffffff, 0x1b082d, |
0x3500, 0xffffffff, 0x87, |
0x3504, 0xffffffff, 0x310851, |
0x3500, 0xffffffff, 0xba, |
0x3504, 0xffffffff, 0x891, |
0x3500, 0xffffffff, 0xbc, |
0x3504, 0xffffffff, 0x893, |
0x3500, 0xffffffff, 0xbe, |
0x3504, 0xffffffff, 0x20895, |
0x3500, 0xffffffff, 0xc2, |
0x3504, 0xffffffff, 0x20899, |
0x3500, 0xffffffff, 0xc6, |
0x3504, 0xffffffff, 0x2089d, |
0x3500, 0xffffffff, 0xca, |
0x3504, 0xffffffff, 0x8a1, |
0x3500, 0xffffffff, 0xcc, |
0x3504, 0xffffffff, 0x8a3, |
0x3500, 0xffffffff, 0xce, |
0x3504, 0xffffffff, 0x308a5, |
0x3500, 0xffffffff, 0xd3, |
0x3504, 0xffffffff, 0x6d08cd, |
0x3500, 0xffffffff, 0x142, |
0x3504, 0xffffffff, 0x2000095a, |
0x3504, 0xffffffff, 0x1, |
0x3500, 0xffffffff, 0x144, |
0x3504, 0xffffffff, 0x301f095b, |
0x3500, 0xffffffff, 0x165, |
0x3504, 0xffffffff, 0xc094d, |
0x3500, 0xffffffff, 0x173, |
0x3504, 0xffffffff, 0xf096d, |
0x3500, 0xffffffff, 0x184, |
0x3504, 0xffffffff, 0x15097f, |
0x3500, 0xffffffff, 0x19b, |
0x3504, 0xffffffff, 0xc0998, |
0x3500, 0xffffffff, 0x1a9, |
0x3504, 0xffffffff, 0x409a7, |
0x3500, 0xffffffff, 0x1af, |
0x3504, 0xffffffff, 0xcdc, |
0x3500, 0xffffffff, 0x1b1, |
0x3504, 0xffffffff, 0x800, |
0x3508, 0xffffffff, 0x6c9b2000, |
0x3510, 0xfc00, 0x2000, |
0x3544, 0xffffffff, 0xfc0, |
0x28d4, 0x00000100, 0x100 |
}; |
static void si_init_golden_registers(struct radeon_device *rdev) |
{ |
switch (rdev->family) { |
case CHIP_TAHITI: |
radeon_program_register_sequence(rdev, |
tahiti_golden_registers, |
(const u32)ARRAY_SIZE(tahiti_golden_registers)); |
radeon_program_register_sequence(rdev, |
tahiti_golden_rlc_registers, |
(const u32)ARRAY_SIZE(tahiti_golden_rlc_registers)); |
radeon_program_register_sequence(rdev, |
tahiti_mgcg_cgcg_init, |
(const u32)ARRAY_SIZE(tahiti_mgcg_cgcg_init)); |
radeon_program_register_sequence(rdev, |
tahiti_golden_registers2, |
(const u32)ARRAY_SIZE(tahiti_golden_registers2)); |
break; |
case CHIP_PITCAIRN: |
radeon_program_register_sequence(rdev, |
pitcairn_golden_registers, |
(const u32)ARRAY_SIZE(pitcairn_golden_registers)); |
radeon_program_register_sequence(rdev, |
pitcairn_golden_rlc_registers, |
(const u32)ARRAY_SIZE(pitcairn_golden_rlc_registers)); |
radeon_program_register_sequence(rdev, |
pitcairn_mgcg_cgcg_init, |
(const u32)ARRAY_SIZE(pitcairn_mgcg_cgcg_init)); |
break; |
case CHIP_VERDE: |
radeon_program_register_sequence(rdev, |
verde_golden_registers, |
(const u32)ARRAY_SIZE(verde_golden_registers)); |
radeon_program_register_sequence(rdev, |
verde_golden_rlc_registers, |
(const u32)ARRAY_SIZE(verde_golden_rlc_registers)); |
radeon_program_register_sequence(rdev, |
verde_mgcg_cgcg_init, |
(const u32)ARRAY_SIZE(verde_mgcg_cgcg_init)); |
radeon_program_register_sequence(rdev, |
verde_pg_init, |
(const u32)ARRAY_SIZE(verde_pg_init)); |
break; |
case CHIP_OLAND: |
radeon_program_register_sequence(rdev, |
oland_golden_registers, |
(const u32)ARRAY_SIZE(oland_golden_registers)); |
radeon_program_register_sequence(rdev, |
oland_golden_rlc_registers, |
(const u32)ARRAY_SIZE(oland_golden_rlc_registers)); |
radeon_program_register_sequence(rdev, |
oland_mgcg_cgcg_init, |
(const u32)ARRAY_SIZE(oland_mgcg_cgcg_init)); |
break; |
case CHIP_HAINAN: |
radeon_program_register_sequence(rdev, |
hainan_golden_registers, |
(const u32)ARRAY_SIZE(hainan_golden_registers)); |
radeon_program_register_sequence(rdev, |
hainan_golden_registers2, |
(const u32)ARRAY_SIZE(hainan_golden_registers2)); |
radeon_program_register_sequence(rdev, |
hainan_mgcg_cgcg_init, |
(const u32)ARRAY_SIZE(hainan_mgcg_cgcg_init)); |
break; |
default: |
break; |
} |
} |
#define PCIE_BUS_CLK 10000 |
#define TCLK (PCIE_BUS_CLK / 10) |
/** |
* si_get_xclk - get the xclk |
* |
* @rdev: radeon_device pointer |
* |
* Returns the reference clock used by the gfx engine |
* (SI). |
*/ |
u32 si_get_xclk(struct radeon_device *rdev) |
{ |
u32 reference_clock = rdev->clock.spll.reference_freq; |
u32 tmp; |
tmp = RREG32(CG_CLKPIN_CNTL_2); |
if (tmp & MUX_TCLK_TO_XCLK) |
return TCLK; |
tmp = RREG32(CG_CLKPIN_CNTL); |
if (tmp & XTALIN_DIVIDE) |
return reference_clock / 4; |
return reference_clock; |
} |
/* get temperature in millidegrees */ |
int si_get_temp(struct radeon_device *rdev) |
{ |
200,6 → 1150,84 |
{0x0000009f, 0x00a37400} |
}; |
static const u32 oland_io_mc_regs[TAHITI_IO_MC_REGS_SIZE][2] = { |
{0x0000006f, 0x03044000}, |
{0x00000070, 0x0480c018}, |
{0x00000071, 0x00000040}, |
{0x00000072, 0x01000000}, |
{0x00000074, 0x000000ff}, |
{0x00000075, 0x00143400}, |
{0x00000076, 0x08ec0800}, |
{0x00000077, 0x040000cc}, |
{0x00000079, 0x00000000}, |
{0x0000007a, 0x21000409}, |
{0x0000007c, 0x00000000}, |
{0x0000007d, 0xe8000000}, |
{0x0000007e, 0x044408a8}, |
{0x0000007f, 0x00000003}, |
{0x00000080, 0x00000000}, |
{0x00000081, 0x01000000}, |
{0x00000082, 0x02000000}, |
{0x00000083, 0x00000000}, |
{0x00000084, 0xe3f3e4f4}, |
{0x00000085, 0x00052024}, |
{0x00000087, 0x00000000}, |
{0x00000088, 0x66036603}, |
{0x00000089, 0x01000000}, |
{0x0000008b, 0x1c0a0000}, |
{0x0000008c, 0xff010000}, |
{0x0000008e, 0xffffefff}, |
{0x0000008f, 0xfff3efff}, |
{0x00000090, 0xfff3efbf}, |
{0x00000094, 0x00101101}, |
{0x00000095, 0x00000fff}, |
{0x00000096, 0x00116fff}, |
{0x00000097, 0x60010000}, |
{0x00000098, 0x10010000}, |
{0x00000099, 0x00006000}, |
{0x0000009a, 0x00001000}, |
{0x0000009f, 0x00a17730} |
}; |
static const u32 hainan_io_mc_regs[TAHITI_IO_MC_REGS_SIZE][2] = { |
{0x0000006f, 0x03044000}, |
{0x00000070, 0x0480c018}, |
{0x00000071, 0x00000040}, |
{0x00000072, 0x01000000}, |
{0x00000074, 0x000000ff}, |
{0x00000075, 0x00143400}, |
{0x00000076, 0x08ec0800}, |
{0x00000077, 0x040000cc}, |
{0x00000079, 0x00000000}, |
{0x0000007a, 0x21000409}, |
{0x0000007c, 0x00000000}, |
{0x0000007d, 0xe8000000}, |
{0x0000007e, 0x044408a8}, |
{0x0000007f, 0x00000003}, |
{0x00000080, 0x00000000}, |
{0x00000081, 0x01000000}, |
{0x00000082, 0x02000000}, |
{0x00000083, 0x00000000}, |
{0x00000084, 0xe3f3e4f4}, |
{0x00000085, 0x00052024}, |
{0x00000087, 0x00000000}, |
{0x00000088, 0x66036603}, |
{0x00000089, 0x01000000}, |
{0x0000008b, 0x1c0a0000}, |
{0x0000008c, 0xff010000}, |
{0x0000008e, 0xffffefff}, |
{0x0000008f, 0xfff3efff}, |
{0x00000090, 0xfff3efbf}, |
{0x00000094, 0x00101101}, |
{0x00000095, 0x00000fff}, |
{0x00000096, 0x00116fff}, |
{0x00000097, 0x60010000}, |
{0x00000098, 0x10010000}, |
{0x00000099, 0x00006000}, |
{0x0000009a, 0x00001000}, |
{0x0000009f, 0x00a07730} |
}; |
/* ucode loading */ |
static int si_mc_load_microcode(struct radeon_device *rdev) |
{ |
228,6 → 1256,16 |
ucode_size = SI_MC_UCODE_SIZE; |
regs_size = TAHITI_IO_MC_REGS_SIZE; |
break; |
case CHIP_OLAND: |
io_mc_regs = (u32 *)&oland_io_mc_regs; |
ucode_size = OLAND_MC_UCODE_SIZE; |
regs_size = TAHITI_IO_MC_REGS_SIZE; |
break; |
case CHIP_HAINAN: |
io_mc_regs = (u32 *)&hainan_io_mc_regs; |
ucode_size = OLAND_MC_UCODE_SIZE; |
regs_size = TAHITI_IO_MC_REGS_SIZE; |
break; |
} |
running = RREG32(MC_SEQ_SUP_CNTL) & RUN_MASK; |
322,6 → 1360,24 |
rlc_req_size = SI_RLC_UCODE_SIZE * 4; |
mc_req_size = SI_MC_UCODE_SIZE * 4; |
break; |
case CHIP_OLAND: |
chip_name = "OLAND"; |
rlc_chip_name = "OLAND"; |
pfp_req_size = SI_PFP_UCODE_SIZE * 4; |
me_req_size = SI_PM4_UCODE_SIZE * 4; |
ce_req_size = SI_CE_UCODE_SIZE * 4; |
rlc_req_size = SI_RLC_UCODE_SIZE * 4; |
mc_req_size = OLAND_MC_UCODE_SIZE * 4; |
break; |
case CHIP_HAINAN: |
chip_name = "HAINAN"; |
rlc_chip_name = "HAINAN"; |
pfp_req_size = SI_PFP_UCODE_SIZE * 4; |
me_req_size = SI_PM4_UCODE_SIZE * 4; |
ce_req_size = SI_CE_UCODE_SIZE * 4; |
rlc_req_size = SI_RLC_UCODE_SIZE * 4; |
mc_req_size = OLAND_MC_UCODE_SIZE * 4; |
break; |
default: BUG(); |
} |
1123,9 → 2179,12 |
gb_tile_moden = 0; |
break; |
} |
rdev->config.si.tile_mode_array[reg_offset] = gb_tile_moden; |
WREG32(GB_TILE_MODE0 + (reg_offset * 4), gb_tile_moden); |
} |
} else if (rdev->family == CHIP_VERDE) { |
} else if ((rdev->family == CHIP_VERDE) || |
(rdev->family == CHIP_OLAND) || |
(rdev->family == CHIP_HAINAN)) { |
for (reg_offset = 0; reg_offset < num_tile_mode_states; reg_offset++) { |
switch (reg_offset) { |
case 0: /* non-AA compressed depth or any compressed stencil */ |
1362,6 → 2421,7 |
gb_tile_moden = 0; |
break; |
} |
rdev->config.si.tile_mode_array[reg_offset] = gb_tile_moden; |
WREG32(GB_TILE_MODE0 + (reg_offset * 4), gb_tile_moden); |
} |
} else |
1374,7 → 2434,7 |
u32 data = INSTANCE_BROADCAST_WRITES; |
if ((se_num == 0xffffffff) && (sh_num == 0xffffffff)) |
data = SH_BROADCAST_WRITES | SE_BROADCAST_WRITES; |
data |= SH_BROADCAST_WRITES | SE_BROADCAST_WRITES; |
else if (se_num == 0xffffffff) |
data |= SE_BROADCAST_WRITES | SH_INDEX(sh_num); |
else if (sh_num == 0xffffffff) |
1556,7 → 2616,7 |
default: |
rdev->config.si.max_shader_engines = 1; |
rdev->config.si.max_tile_pipes = 4; |
rdev->config.si.max_cu_per_sh = 2; |
rdev->config.si.max_cu_per_sh = 5; |
rdev->config.si.max_sh_per_se = 2; |
rdev->config.si.max_backends_per_se = 4; |
rdev->config.si.max_texture_channel_caches = 4; |
1570,6 → 2630,40 |
rdev->config.si.sc_earlyz_tile_fifo_size = 0x130; |
gb_addr_config = VERDE_GB_ADDR_CONFIG_GOLDEN; |
break; |
case CHIP_OLAND: |
rdev->config.si.max_shader_engines = 1; |
rdev->config.si.max_tile_pipes = 4; |
rdev->config.si.max_cu_per_sh = 6; |
rdev->config.si.max_sh_per_se = 1; |
rdev->config.si.max_backends_per_se = 2; |
rdev->config.si.max_texture_channel_caches = 4; |
rdev->config.si.max_gprs = 256; |
rdev->config.si.max_gs_threads = 16; |
rdev->config.si.max_hw_contexts = 8; |
rdev->config.si.sc_prim_fifo_size_frontend = 0x20; |
rdev->config.si.sc_prim_fifo_size_backend = 0x40; |
rdev->config.si.sc_hiz_tile_fifo_size = 0x30; |
rdev->config.si.sc_earlyz_tile_fifo_size = 0x130; |
gb_addr_config = VERDE_GB_ADDR_CONFIG_GOLDEN; |
break; |
case CHIP_HAINAN: |
rdev->config.si.max_shader_engines = 1; |
rdev->config.si.max_tile_pipes = 4; |
rdev->config.si.max_cu_per_sh = 5; |
rdev->config.si.max_sh_per_se = 1; |
rdev->config.si.max_backends_per_se = 1; |
rdev->config.si.max_texture_channel_caches = 2; |
rdev->config.si.max_gprs = 256; |
rdev->config.si.max_gs_threads = 16; |
rdev->config.si.max_hw_contexts = 8; |
rdev->config.si.sc_prim_fifo_size_frontend = 0x20; |
rdev->config.si.sc_prim_fifo_size_backend = 0x40; |
rdev->config.si.sc_hiz_tile_fifo_size = 0x30; |
rdev->config.si.sc_earlyz_tile_fifo_size = 0x130; |
gb_addr_config = HAINAN_GB_ADDR_CONFIG_GOLDEN; |
break; |
} |
/* Initialize HDP */ |
1659,9 → 2753,15 |
WREG32(GB_ADDR_CONFIG, gb_addr_config); |
WREG32(DMIF_ADDR_CONFIG, gb_addr_config); |
WREG32(DMIF_ADDR_CALC, gb_addr_config); |
WREG32(HDP_ADDR_CONFIG, gb_addr_config); |
WREG32(DMA_TILING_CONFIG + DMA0_REGISTER_OFFSET, gb_addr_config); |
WREG32(DMA_TILING_CONFIG + DMA1_REGISTER_OFFSET, gb_addr_config); |
if (rdev->has_uvd) { |
WREG32(UVD_UDEC_ADDR_CONFIG, gb_addr_config); |
WREG32(UVD_UDEC_DB_ADDR_CONFIG, gb_addr_config); |
WREG32(UVD_UDEC_DBW_ADDR_CONFIG, gb_addr_config); |
} |
si_tiling_mode_table_init(rdev); |
2106,50 → 3206,129 |
return 0; |
} |
bool si_gpu_is_lockup(struct radeon_device *rdev, struct radeon_ring *ring) |
static u32 si_gpu_check_soft_reset(struct radeon_device *rdev) |
{ |
u32 srbm_status; |
u32 grbm_status, grbm_status2; |
u32 grbm_status_se0, grbm_status_se1; |
u32 reset_mask = 0; |
u32 tmp; |
srbm_status = RREG32(SRBM_STATUS); |
grbm_status = RREG32(GRBM_STATUS); |
grbm_status2 = RREG32(GRBM_STATUS2); |
grbm_status_se0 = RREG32(GRBM_STATUS_SE0); |
grbm_status_se1 = RREG32(GRBM_STATUS_SE1); |
if (!(grbm_status & GUI_ACTIVE)) { |
radeon_ring_lockup_update(ring); |
return false; |
/* GRBM_STATUS */ |
tmp = RREG32(GRBM_STATUS); |
if (tmp & (PA_BUSY | SC_BUSY | |
BCI_BUSY | SX_BUSY | |
TA_BUSY | VGT_BUSY | |
DB_BUSY | CB_BUSY | |
GDS_BUSY | SPI_BUSY | |
IA_BUSY | IA_BUSY_NO_DMA)) |
reset_mask |= RADEON_RESET_GFX; |
if (tmp & (CF_RQ_PENDING | PF_RQ_PENDING | |
CP_BUSY | CP_COHERENCY_BUSY)) |
reset_mask |= RADEON_RESET_CP; |
if (tmp & GRBM_EE_BUSY) |
reset_mask |= RADEON_RESET_GRBM | RADEON_RESET_GFX | RADEON_RESET_CP; |
/* GRBM_STATUS2 */ |
tmp = RREG32(GRBM_STATUS2); |
if (tmp & (RLC_RQ_PENDING | RLC_BUSY)) |
reset_mask |= RADEON_RESET_RLC; |
/* DMA_STATUS_REG 0 */ |
tmp = RREG32(DMA_STATUS_REG + DMA0_REGISTER_OFFSET); |
if (!(tmp & DMA_IDLE)) |
reset_mask |= RADEON_RESET_DMA; |
/* DMA_STATUS_REG 1 */ |
tmp = RREG32(DMA_STATUS_REG + DMA1_REGISTER_OFFSET); |
if (!(tmp & DMA_IDLE)) |
reset_mask |= RADEON_RESET_DMA1; |
/* SRBM_STATUS2 */ |
tmp = RREG32(SRBM_STATUS2); |
if (tmp & DMA_BUSY) |
reset_mask |= RADEON_RESET_DMA; |
if (tmp & DMA1_BUSY) |
reset_mask |= RADEON_RESET_DMA1; |
/* SRBM_STATUS */ |
tmp = RREG32(SRBM_STATUS); |
if (tmp & IH_BUSY) |
reset_mask |= RADEON_RESET_IH; |
if (tmp & SEM_BUSY) |
reset_mask |= RADEON_RESET_SEM; |
if (tmp & GRBM_RQ_PENDING) |
reset_mask |= RADEON_RESET_GRBM; |
if (tmp & VMC_BUSY) |
reset_mask |= RADEON_RESET_VMC; |
if (tmp & (MCB_BUSY | MCB_NON_DISPLAY_BUSY | |
MCC_BUSY | MCD_BUSY)) |
reset_mask |= RADEON_RESET_MC; |
if (evergreen_is_display_hung(rdev)) |
reset_mask |= RADEON_RESET_DISPLAY; |
/* VM_L2_STATUS */ |
tmp = RREG32(VM_L2_STATUS); |
if (tmp & L2_BUSY) |
reset_mask |= RADEON_RESET_VMC; |
/* Skip MC reset as it's mostly likely not hung, just busy */ |
if (reset_mask & RADEON_RESET_MC) { |
DRM_DEBUG("MC busy: 0x%08X, clearing.\n", reset_mask); |
reset_mask &= ~RADEON_RESET_MC; |
} |
/* force CP activities */ |
radeon_ring_force_activity(rdev, ring); |
return radeon_ring_test_lockup(rdev, ring); |
return reset_mask; |
} |
static void si_gpu_soft_reset_gfx(struct radeon_device *rdev) |
static void si_gpu_soft_reset(struct radeon_device *rdev, u32 reset_mask) |
{ |
u32 grbm_reset = 0; |
struct evergreen_mc_save save; |
u32 grbm_soft_reset = 0, srbm_soft_reset = 0; |
u32 tmp; |
if (!(RREG32(GRBM_STATUS) & GUI_ACTIVE)) |
if (reset_mask == 0) |
return; |
dev_info(rdev->dev, " GRBM_STATUS=0x%08X\n", |
RREG32(GRBM_STATUS)); |
dev_info(rdev->dev, " GRBM_STATUS2=0x%08X\n", |
RREG32(GRBM_STATUS2)); |
dev_info(rdev->dev, " GRBM_STATUS_SE0=0x%08X\n", |
RREG32(GRBM_STATUS_SE0)); |
dev_info(rdev->dev, " GRBM_STATUS_SE1=0x%08X\n", |
RREG32(GRBM_STATUS_SE1)); |
dev_info(rdev->dev, " SRBM_STATUS=0x%08X\n", |
RREG32(SRBM_STATUS)); |
dev_info(rdev->dev, "GPU softreset: 0x%08X\n", reset_mask); |
evergreen_print_gpu_status_regs(rdev); |
dev_info(rdev->dev, " VM_CONTEXT1_PROTECTION_FAULT_ADDR 0x%08X\n", |
RREG32(VM_CONTEXT1_PROTECTION_FAULT_ADDR)); |
dev_info(rdev->dev, " VM_CONTEXT1_PROTECTION_FAULT_STATUS 0x%08X\n", |
RREG32(VM_CONTEXT1_PROTECTION_FAULT_STATUS)); |
/* Disable CP parsing/prefetching */ |
WREG32(CP_ME_CNTL, CP_ME_HALT | CP_PFP_HALT | CP_CE_HALT); |
/* reset all the gfx blocks */ |
grbm_reset = (SOFT_RESET_CP | |
SOFT_RESET_CB | |
if (reset_mask & RADEON_RESET_DMA) { |
/* dma0 */ |
tmp = RREG32(DMA_RB_CNTL + DMA0_REGISTER_OFFSET); |
tmp &= ~DMA_RB_ENABLE; |
WREG32(DMA_RB_CNTL + DMA0_REGISTER_OFFSET, tmp); |
} |
if (reset_mask & RADEON_RESET_DMA1) { |
/* dma1 */ |
tmp = RREG32(DMA_RB_CNTL + DMA1_REGISTER_OFFSET); |
tmp &= ~DMA_RB_ENABLE; |
WREG32(DMA_RB_CNTL + DMA1_REGISTER_OFFSET, tmp); |
} |
udelay(50); |
evergreen_mc_stop(rdev, &save); |
if (evergreen_mc_wait_for_idle(rdev)) { |
dev_warn(rdev->dev, "Wait for MC idle timedout !\n"); |
} |
if (reset_mask & (RADEON_RESET_GFX | RADEON_RESET_COMPUTE | RADEON_RESET_CP)) { |
grbm_soft_reset = SOFT_RESET_CB | |
SOFT_RESET_DB | |
SOFT_RESET_GDS | |
SOFT_RESET_PA | |
2160,96 → 3339,150 |
SOFT_RESET_TC | |
SOFT_RESET_TA | |
SOFT_RESET_VGT | |
SOFT_RESET_IA); |
SOFT_RESET_IA; |
} |
dev_info(rdev->dev, " GRBM_SOFT_RESET=0x%08X\n", grbm_reset); |
WREG32(GRBM_SOFT_RESET, grbm_reset); |
(void)RREG32(GRBM_SOFT_RESET); |
udelay(50); |
WREG32(GRBM_SOFT_RESET, 0); |
(void)RREG32(GRBM_SOFT_RESET); |
if (reset_mask & RADEON_RESET_CP) { |
grbm_soft_reset |= SOFT_RESET_CP | SOFT_RESET_VGT; |
dev_info(rdev->dev, " GRBM_STATUS=0x%08X\n", |
RREG32(GRBM_STATUS)); |
dev_info(rdev->dev, " GRBM_STATUS2=0x%08X\n", |
RREG32(GRBM_STATUS2)); |
dev_info(rdev->dev, " GRBM_STATUS_SE0=0x%08X\n", |
RREG32(GRBM_STATUS_SE0)); |
dev_info(rdev->dev, " GRBM_STATUS_SE1=0x%08X\n", |
RREG32(GRBM_STATUS_SE1)); |
dev_info(rdev->dev, " SRBM_STATUS=0x%08X\n", |
RREG32(SRBM_STATUS)); |
srbm_soft_reset |= SOFT_RESET_GRBM; |
} |
static void si_gpu_soft_reset_dma(struct radeon_device *rdev) |
{ |
u32 tmp; |
if (reset_mask & RADEON_RESET_DMA) |
srbm_soft_reset |= SOFT_RESET_DMA; |
if (RREG32(DMA_STATUS_REG) & DMA_IDLE) |
return; |
if (reset_mask & RADEON_RESET_DMA1) |
srbm_soft_reset |= SOFT_RESET_DMA1; |
dev_info(rdev->dev, " DMA_STATUS_REG = 0x%08X\n", |
RREG32(DMA_STATUS_REG)); |
if (reset_mask & RADEON_RESET_DISPLAY) |
srbm_soft_reset |= SOFT_RESET_DC; |
/* dma0 */ |
tmp = RREG32(DMA_RB_CNTL + DMA0_REGISTER_OFFSET); |
tmp &= ~DMA_RB_ENABLE; |
WREG32(DMA_RB_CNTL + DMA0_REGISTER_OFFSET, tmp); |
if (reset_mask & RADEON_RESET_RLC) |
grbm_soft_reset |= SOFT_RESET_RLC; |
/* dma1 */ |
tmp = RREG32(DMA_RB_CNTL + DMA1_REGISTER_OFFSET); |
tmp &= ~DMA_RB_ENABLE; |
WREG32(DMA_RB_CNTL + DMA1_REGISTER_OFFSET, tmp); |
if (reset_mask & RADEON_RESET_SEM) |
srbm_soft_reset |= SOFT_RESET_SEM; |
/* Reset dma */ |
WREG32(SRBM_SOFT_RESET, SOFT_RESET_DMA | SOFT_RESET_DMA1); |
RREG32(SRBM_SOFT_RESET); |
udelay(50); |
WREG32(SRBM_SOFT_RESET, 0); |
if (reset_mask & RADEON_RESET_IH) |
srbm_soft_reset |= SOFT_RESET_IH; |
dev_info(rdev->dev, " DMA_STATUS_REG = 0x%08X\n", |
RREG32(DMA_STATUS_REG)); |
} |
if (reset_mask & RADEON_RESET_GRBM) |
srbm_soft_reset |= SOFT_RESET_GRBM; |
static int si_gpu_soft_reset(struct radeon_device *rdev, u32 reset_mask) |
{ |
struct evergreen_mc_save save; |
if (reset_mask & RADEON_RESET_VMC) |
srbm_soft_reset |= SOFT_RESET_VMC; |
if (reset_mask == 0) |
return 0; |
if (reset_mask & RADEON_RESET_MC) |
srbm_soft_reset |= SOFT_RESET_MC; |
dev_info(rdev->dev, "GPU softreset: 0x%08X\n", reset_mask); |
if (grbm_soft_reset) { |
tmp = RREG32(GRBM_SOFT_RESET); |
tmp |= grbm_soft_reset; |
dev_info(rdev->dev, "GRBM_SOFT_RESET=0x%08X\n", tmp); |
WREG32(GRBM_SOFT_RESET, tmp); |
tmp = RREG32(GRBM_SOFT_RESET); |
dev_info(rdev->dev, " VM_CONTEXT1_PROTECTION_FAULT_ADDR 0x%08X\n", |
RREG32(VM_CONTEXT1_PROTECTION_FAULT_ADDR)); |
dev_info(rdev->dev, " VM_CONTEXT1_PROTECTION_FAULT_STATUS 0x%08X\n", |
RREG32(VM_CONTEXT1_PROTECTION_FAULT_STATUS)); |
udelay(50); |
evergreen_mc_stop(rdev, &save); |
if (radeon_mc_wait_for_idle(rdev)) { |
dev_warn(rdev->dev, "Wait for MC idle timedout !\n"); |
tmp &= ~grbm_soft_reset; |
WREG32(GRBM_SOFT_RESET, tmp); |
tmp = RREG32(GRBM_SOFT_RESET); |
} |
if (reset_mask & (RADEON_RESET_GFX | RADEON_RESET_COMPUTE)) |
si_gpu_soft_reset_gfx(rdev); |
if (srbm_soft_reset) { |
tmp = RREG32(SRBM_SOFT_RESET); |
tmp |= srbm_soft_reset; |
dev_info(rdev->dev, "SRBM_SOFT_RESET=0x%08X\n", tmp); |
WREG32(SRBM_SOFT_RESET, tmp); |
tmp = RREG32(SRBM_SOFT_RESET); |
if (reset_mask & RADEON_RESET_DMA) |
si_gpu_soft_reset_dma(rdev); |
udelay(50); |
tmp &= ~srbm_soft_reset; |
WREG32(SRBM_SOFT_RESET, tmp); |
tmp = RREG32(SRBM_SOFT_RESET); |
} |
/* Wait a little for things to settle down */ |
udelay(50); |
evergreen_mc_resume(rdev, &save); |
return 0; |
udelay(50); |
evergreen_print_gpu_status_regs(rdev); |
} |
int si_asic_reset(struct radeon_device *rdev) |
{ |
return si_gpu_soft_reset(rdev, (RADEON_RESET_GFX | |
u32 reset_mask; |
reset_mask = si_gpu_check_soft_reset(rdev); |
if (reset_mask) |
r600_set_bios_scratch_engine_hung(rdev, true); |
si_gpu_soft_reset(rdev, reset_mask); |
reset_mask = si_gpu_check_soft_reset(rdev); |
if (!reset_mask) |
r600_set_bios_scratch_engine_hung(rdev, false); |
return 0; |
} |
/** |
* si_gfx_is_lockup - Check if the GFX engine is locked up |
* |
* @rdev: radeon_device pointer |
* @ring: radeon_ring structure holding ring information |
* |
* Check if the GFX engine is locked up. |
* Returns true if the engine appears to be locked up, false if not. |
*/ |
bool si_gfx_is_lockup(struct radeon_device *rdev, struct radeon_ring *ring) |
{ |
u32 reset_mask = si_gpu_check_soft_reset(rdev); |
if (!(reset_mask & (RADEON_RESET_GFX | |
RADEON_RESET_COMPUTE | |
RADEON_RESET_DMA)); |
RADEON_RESET_CP))) { |
radeon_ring_lockup_update(ring); |
return false; |
} |
/* force CP activities */ |
radeon_ring_force_activity(rdev, ring); |
return radeon_ring_test_lockup(rdev, ring); |
} |
/** |
* si_dma_is_lockup - Check if the DMA engine is locked up |
* |
* @rdev: radeon_device pointer |
* @ring: radeon_ring structure holding ring information |
* |
* Check if the async DMA engine is locked up. |
* Returns true if the engine appears to be locked up, false if not. |
*/ |
bool si_dma_is_lockup(struct radeon_device *rdev, struct radeon_ring *ring) |
{ |
u32 reset_mask = si_gpu_check_soft_reset(rdev); |
u32 mask; |
if (ring->idx == R600_RING_TYPE_DMA_INDEX) |
mask = RADEON_RESET_DMA; |
else |
mask = RADEON_RESET_DMA1; |
if (!(reset_mask & mask)) { |
radeon_ring_lockup_update(ring); |
return false; |
} |
/* force ring activities */ |
radeon_ring_force_activity(rdev, ring); |
return radeon_ring_test_lockup(rdev, ring); |
} |
/* MC */ |
static void si_mc_program(struct radeon_device *rdev) |
{ |
2271,6 → 3504,7 |
if (radeon_mc_wait_for_idle(rdev)) { |
dev_warn(rdev->dev, "Wait for MC idle timedout !\n"); |
} |
if (!ASIC_IS_NODCE(rdev)) |
/* Lockout access through VGA aperture*/ |
WREG32(VGA_HDP_CONTROL, VGA_MEMORY_DISABLE); |
/* Update configuration */ |
2294,51 → 3528,13 |
dev_warn(rdev->dev, "Wait for MC idle timedout !\n"); |
} |
evergreen_mc_resume(rdev, &save); |
if (!ASIC_IS_NODCE(rdev)) { |
/* we need to own VRAM, so turn off the VGA renderer here |
* to stop it overwriting our objects */ |
rv515_vga_render_disable(rdev); |
} |
/* SI MC address space is 40 bits */ |
static void si_vram_location(struct radeon_device *rdev, |
struct radeon_mc *mc, u64 base) |
{ |
mc->vram_start = base; |
if (mc->mc_vram_size > (0xFFFFFFFFFFULL - base + 1)) { |
dev_warn(rdev->dev, "limiting VRAM to PCI aperture size\n"); |
mc->real_vram_size = mc->aper_size; |
mc->mc_vram_size = mc->aper_size; |
} |
mc->vram_end = mc->vram_start + mc->mc_vram_size - 1; |
dev_info(rdev->dev, "VRAM: %lluM 0x%016llX - 0x%016llX (%lluM used)\n", |
mc->mc_vram_size >> 20, mc->vram_start, |
mc->vram_end, mc->real_vram_size >> 20); |
} |
static void si_gtt_location(struct radeon_device *rdev, struct radeon_mc *mc) |
{ |
u64 size_af, size_bf; |
size_af = ((0xFFFFFFFFFFULL - mc->vram_end) + mc->gtt_base_align) & ~mc->gtt_base_align; |
size_bf = mc->vram_start & ~mc->gtt_base_align; |
if (size_bf > size_af) { |
if (mc->gtt_size > size_bf) { |
dev_warn(rdev->dev, "limiting GTT\n"); |
mc->gtt_size = size_bf; |
} |
mc->gtt_start = (mc->vram_start & ~mc->gtt_base_align) - mc->gtt_size; |
} else { |
if (mc->gtt_size > size_af) { |
dev_warn(rdev->dev, "limiting GTT\n"); |
mc->gtt_size = size_af; |
} |
mc->gtt_start = (mc->vram_end + 1 + mc->gtt_base_align) & ~mc->gtt_base_align; |
} |
mc->gtt_end = mc->gtt_start + mc->gtt_size - 1; |
dev_info(rdev->dev, "GTT: %lluM 0x%016llX - 0x%016llX\n", |
mc->gtt_size >> 20, mc->gtt_start, mc->gtt_end); |
} |
static void si_vram_gtt_location(struct radeon_device *rdev, |
struct radeon_mc *mc) |
{ |
2348,9 → 3544,9 |
mc->real_vram_size = 0xFFC0000000ULL; |
mc->mc_vram_size = 0xFFC0000000ULL; |
} |
si_vram_location(rdev, &rdev->mc, 0); |
radeon_vram_location(rdev, &rdev->mc, 0); |
rdev->mc.gtt_base_align = 0; |
si_gtt_location(rdev, mc); |
radeon_gtt_location(rdev, mc); |
} |
static int si_mc_init(struct radeon_device *rdev) |
2404,8 → 3600,8 |
rdev->mc.aper_base = pci_resource_start(rdev->pdev, 0); |
rdev->mc.aper_size = pci_resource_len(rdev->pdev, 0); |
/* size in MB on si */ |
rdev->mc.mc_vram_size = RREG32(CONFIG_MEMSIZE) * 1024 * 1024; |
rdev->mc.real_vram_size = RREG32(CONFIG_MEMSIZE) * 1024 * 1024; |
rdev->mc.mc_vram_size = RREG32(CONFIG_MEMSIZE) * 1024ULL * 1024ULL; |
rdev->mc.real_vram_size = RREG32(CONFIG_MEMSIZE) * 1024ULL * 1024ULL; |
rdev->mc.visible_vram_size = rdev->mc.aper_size; |
si_vram_gtt_location(rdev, &rdev->mc); |
radeon_update_bandwidth_info(rdev); |
2849,19 → 4045,19 |
do { |
pkt.idx = idx; |
pkt.type = CP_PACKET_GET_TYPE(ib->ptr[idx]); |
pkt.count = CP_PACKET_GET_COUNT(ib->ptr[idx]); |
pkt.type = RADEON_CP_PACKET_GET_TYPE(ib->ptr[idx]); |
pkt.count = RADEON_CP_PACKET_GET_COUNT(ib->ptr[idx]); |
pkt.one_reg_wr = 0; |
switch (pkt.type) { |
case PACKET_TYPE0: |
case RADEON_PACKET_TYPE0: |
dev_err(rdev->dev, "Packet0 not allowed!\n"); |
ret = -EINVAL; |
break; |
case PACKET_TYPE2: |
case RADEON_PACKET_TYPE2: |
idx += 1; |
break; |
case PACKET_TYPE3: |
pkt.opcode = CP_PACKET3_GET_OPCODE(ib->ptr[idx]); |
case RADEON_PACKET_TYPE3: |
pkt.opcode = RADEON_CP_PACKET3_GET_OPCODE(ib->ptr[idx]); |
if (ib->is_const_ib) |
ret = si_vm_packet3_ce_check(rdev, ib->ptr, &pkt); |
else { |
2914,6 → 4110,7 |
* si_vm_set_page - update the page tables using the CP |
* |
* @rdev: radeon_device pointer |
* @ib: indirect buffer to fill with commands |
* @pe: addr of the page entry |
* @addr: dst addr to write into pe |
* @count: number of page entries to update |
2920,13 → 4117,14 |
* @incr: increase next addr by incr bytes |
* @flags: access flags |
* |
* Update the page tables using the CP (cayman-si). |
* Update the page tables using the CP (SI). |
*/ |
void si_vm_set_page(struct radeon_device *rdev, uint64_t pe, |
void si_vm_set_page(struct radeon_device *rdev, |
struct radeon_ib *ib, |
uint64_t pe, |
uint64_t addr, unsigned count, |
uint32_t incr, uint32_t flags) |
{ |
struct radeon_ring *ring = &rdev->ring[rdev->asic->vm.pt_ring_index]; |
uint32_t r600_flags = cayman_vm_page_flags(rdev, flags); |
uint64_t value; |
unsigned ndw; |
2937,11 → 4135,11 |
if (ndw > 0x3FFE) |
ndw = 0x3FFE; |
radeon_ring_write(ring, PACKET3(PACKET3_WRITE_DATA, ndw)); |
radeon_ring_write(ring, (WRITE_DATA_ENGINE_SEL(0) | |
WRITE_DATA_DST_SEL(1))); |
radeon_ring_write(ring, pe); |
radeon_ring_write(ring, upper_32_bits(pe)); |
ib->ptr[ib->length_dw++] = PACKET3(PACKET3_WRITE_DATA, ndw); |
ib->ptr[ib->length_dw++] = (WRITE_DATA_ENGINE_SEL(0) | |
WRITE_DATA_DST_SEL(1)); |
ib->ptr[ib->length_dw++] = pe; |
ib->ptr[ib->length_dw++] = upper_32_bits(pe); |
for (; ndw > 2; ndw -= 2, --count, pe += 8) { |
if (flags & RADEON_VM_PAGE_SYSTEM) { |
value = radeon_vm_map_gart(rdev, addr); |
2953,8 → 4151,8 |
} |
addr += incr; |
value |= r600_flags; |
radeon_ring_write(ring, value); |
radeon_ring_write(ring, upper_32_bits(value)); |
ib->ptr[ib->length_dw++] = value; |
ib->ptr[ib->length_dw++] = upper_32_bits(value); |
} |
} |
} else { |
2966,9 → 4164,9 |
ndw = 0xFFFFE; |
/* for non-physically contiguous pages (system) */ |
radeon_ring_write(ring, DMA_PACKET(DMA_PACKET_WRITE, 0, 0, 0, ndw)); |
radeon_ring_write(ring, pe); |
radeon_ring_write(ring, upper_32_bits(pe) & 0xff); |
ib->ptr[ib->length_dw++] = DMA_PACKET(DMA_PACKET_WRITE, 0, 0, 0, ndw); |
ib->ptr[ib->length_dw++] = pe; |
ib->ptr[ib->length_dw++] = upper_32_bits(pe) & 0xff; |
for (; ndw > 0; ndw -= 2, --count, pe += 8) { |
if (flags & RADEON_VM_PAGE_SYSTEM) { |
value = radeon_vm_map_gart(rdev, addr); |
2980,8 → 4178,8 |
} |
addr += incr; |
value |= r600_flags; |
radeon_ring_write(ring, value); |
radeon_ring_write(ring, upper_32_bits(value)); |
ib->ptr[ib->length_dw++] = value; |
ib->ptr[ib->length_dw++] = upper_32_bits(value); |
} |
} |
} else { |
2995,20 → 4193,22 |
else |
value = 0; |
/* for physically contiguous pages (vram) */ |
radeon_ring_write(ring, DMA_PTE_PDE_PACKET(ndw)); |
radeon_ring_write(ring, pe); /* dst addr */ |
radeon_ring_write(ring, upper_32_bits(pe) & 0xff); |
radeon_ring_write(ring, r600_flags); /* mask */ |
radeon_ring_write(ring, 0); |
radeon_ring_write(ring, value); /* value */ |
radeon_ring_write(ring, upper_32_bits(value)); |
radeon_ring_write(ring, incr); /* increment size */ |
radeon_ring_write(ring, 0); |
ib->ptr[ib->length_dw++] = DMA_PTE_PDE_PACKET(ndw); |
ib->ptr[ib->length_dw++] = pe; /* dst addr */ |
ib->ptr[ib->length_dw++] = upper_32_bits(pe) & 0xff; |
ib->ptr[ib->length_dw++] = r600_flags; /* mask */ |
ib->ptr[ib->length_dw++] = 0; |
ib->ptr[ib->length_dw++] = value; /* value */ |
ib->ptr[ib->length_dw++] = upper_32_bits(value); |
ib->ptr[ib->length_dw++] = incr; /* increment size */ |
ib->ptr[ib->length_dw++] = 0; |
pe += ndw * 4; |
addr += (ndw / 2) * incr; |
count -= ndw / 2; |
} |
} |
while (ib->length_dw & 0x7) |
ib->ptr[ib->length_dw++] = DMA_PACKET(DMA_PACKET_NOP, 0, 0, 0, 0); |
} |
} |
3254,8 → 4454,10 |
tmp = RREG32(DMA_CNTL + DMA1_REGISTER_OFFSET) & ~TRAP_ENABLE; |
WREG32(DMA_CNTL + DMA1_REGISTER_OFFSET, tmp); |
WREG32(GRBM_INT_CNTL, 0); |
if (rdev->num_crtc >= 2) { |
WREG32(INT_MASK + EVERGREEN_CRTC0_REGISTER_OFFSET, 0); |
WREG32(INT_MASK + EVERGREEN_CRTC1_REGISTER_OFFSET, 0); |
} |
if (rdev->num_crtc >= 4) { |
WREG32(INT_MASK + EVERGREEN_CRTC2_REGISTER_OFFSET, 0); |
WREG32(INT_MASK + EVERGREEN_CRTC3_REGISTER_OFFSET, 0); |
3265,8 → 4467,10 |
WREG32(INT_MASK + EVERGREEN_CRTC5_REGISTER_OFFSET, 0); |
} |
if (rdev->num_crtc >= 2) { |
WREG32(GRPH_INT_CONTROL + EVERGREEN_CRTC0_REGISTER_OFFSET, 0); |
WREG32(GRPH_INT_CONTROL + EVERGREEN_CRTC1_REGISTER_OFFSET, 0); |
} |
if (rdev->num_crtc >= 4) { |
WREG32(GRPH_INT_CONTROL + EVERGREEN_CRTC2_REGISTER_OFFSET, 0); |
WREG32(GRPH_INT_CONTROL + EVERGREEN_CRTC3_REGISTER_OFFSET, 0); |
3276,6 → 4480,7 |
WREG32(GRPH_INT_CONTROL + EVERGREEN_CRTC5_REGISTER_OFFSET, 0); |
} |
if (!ASIC_IS_NODCE(rdev)) { |
WREG32(DACA_AUTODETECT_INT_CONTROL, 0); |
tmp = RREG32(DC_HPD1_INT_CONTROL) & DC_HPDx_INT_POLARITY; |
3290,8 → 4495,8 |
WREG32(DC_HPD5_INT_CONTROL, tmp); |
tmp = RREG32(DC_HPD6_INT_CONTROL) & DC_HPDx_INT_POLARITY; |
WREG32(DC_HPD6_INT_CONTROL, tmp); |
} |
} |
static int si_irq_init(struct radeon_device *rdev) |
{ |
3369,7 → 4574,7 |
u32 cp_int_cntl = CNTX_BUSY_INT_ENABLE | CNTX_EMPTY_INT_ENABLE; |
u32 cp_int_cntl1 = 0, cp_int_cntl2 = 0; |
u32 crtc1 = 0, crtc2 = 0, crtc3 = 0, crtc4 = 0, crtc5 = 0, crtc6 = 0; |
u32 hpd1, hpd2, hpd3, hpd4, hpd5, hpd6; |
u32 hpd1 = 0, hpd2 = 0, hpd3 = 0, hpd4 = 0, hpd5 = 0, hpd6 = 0; |
u32 grbm_int_cntl = 0; |
u32 grph1 = 0, grph2 = 0, grph3 = 0, grph4 = 0, grph5 = 0, grph6 = 0; |
u32 dma_cntl, dma_cntl1; |
3386,6 → 4591,7 |
return 0; |
} |
if (!ASIC_IS_NODCE(rdev)) { |
hpd1 = RREG32(DC_HPD1_INT_CONTROL) & ~DC_HPDx_INT_EN; |
hpd2 = RREG32(DC_HPD2_INT_CONTROL) & ~DC_HPDx_INT_EN; |
hpd3 = RREG32(DC_HPD3_INT_CONTROL) & ~DC_HPDx_INT_EN; |
3392,6 → 4598,7 |
hpd4 = RREG32(DC_HPD4_INT_CONTROL) & ~DC_HPDx_INT_EN; |
hpd5 = RREG32(DC_HPD5_INT_CONTROL) & ~DC_HPDx_INT_EN; |
hpd6 = RREG32(DC_HPD6_INT_CONTROL) & ~DC_HPDx_INT_EN; |
} |
dma_cntl = RREG32(DMA_CNTL + DMA0_REGISTER_OFFSET) & ~TRAP_ENABLE; |
dma_cntl1 = RREG32(DMA_CNTL + DMA1_REGISTER_OFFSET) & ~TRAP_ENABLE; |
3482,8 → 4689,10 |
WREG32(GRBM_INT_CNTL, grbm_int_cntl); |
if (rdev->num_crtc >= 2) { |
WREG32(INT_MASK + EVERGREEN_CRTC0_REGISTER_OFFSET, crtc1); |
WREG32(INT_MASK + EVERGREEN_CRTC1_REGISTER_OFFSET, crtc2); |
} |
if (rdev->num_crtc >= 4) { |
WREG32(INT_MASK + EVERGREEN_CRTC2_REGISTER_OFFSET, crtc3); |
WREG32(INT_MASK + EVERGREEN_CRTC3_REGISTER_OFFSET, crtc4); |
3493,8 → 4702,10 |
WREG32(INT_MASK + EVERGREEN_CRTC5_REGISTER_OFFSET, crtc6); |
} |
if (rdev->num_crtc >= 2) { |
WREG32(GRPH_INT_CONTROL + EVERGREEN_CRTC0_REGISTER_OFFSET, grph1); |
WREG32(GRPH_INT_CONTROL + EVERGREEN_CRTC1_REGISTER_OFFSET, grph2); |
} |
if (rdev->num_crtc >= 4) { |
WREG32(GRPH_INT_CONTROL + EVERGREEN_CRTC2_REGISTER_OFFSET, grph3); |
WREG32(GRPH_INT_CONTROL + EVERGREEN_CRTC3_REGISTER_OFFSET, grph4); |
3504,6 → 4715,7 |
WREG32(GRPH_INT_CONTROL + EVERGREEN_CRTC5_REGISTER_OFFSET, grph6); |
} |
if (!ASIC_IS_NODCE(rdev)) { |
WREG32(DC_HPD1_INT_CONTROL, hpd1); |
WREG32(DC_HPD2_INT_CONTROL, hpd2); |
WREG32(DC_HPD3_INT_CONTROL, hpd3); |
3510,6 → 4722,7 |
WREG32(DC_HPD4_INT_CONTROL, hpd4); |
WREG32(DC_HPD5_INT_CONTROL, hpd5); |
WREG32(DC_HPD6_INT_CONTROL, hpd6); |
} |
return 0; |
} |
3518,6 → 4731,9 |
{ |
u32 tmp; |
if (ASIC_IS_NODCE(rdev)) |
return; |
rdev->irq.stat_regs.evergreen.disp_int = RREG32(DISP_INTERRUPT_STATUS); |
rdev->irq.stat_regs.evergreen.disp_int_cont = RREG32(DISP_INTERRUPT_STATUS_CONTINUE); |
rdev->irq.stat_regs.evergreen.disp_int_cont2 = RREG32(DISP_INTERRUPT_STATUS_CONTINUE2); |
4079,14 → 5295,6 |
return r; |
si_gpu_init(rdev); |
#if 0 |
r = evergreen_blit_init(rdev); |
if (r) { |
r600_blit_fini(rdev); |
rdev->asic->copy = NULL; |
dev_warn(rdev->dev, "failed blitter (%d) falling back to memcpy\n", r); |
} |
#endif |
/* allocate rlc buffers */ |
r = si_rlc_init(rdev); |
if (r) { |
4129,7 → 5337,14 |
return r; |
} |
/* Enable IRQ */ |
if (!rdev->irq.installed) { |
r = radeon_irq_kms_init(rdev); |
if (r) |
return r; |
} |
r = si_irq_init(rdev); |
if (r) { |
DRM_ERROR("radeon: IH init failed (%d).\n", r); |
4186,6 → 5401,7 |
if (r) |
return r; |
r = radeon_ib_pool_init(rdev); |
if (r) { |
dev_err(rdev->dev, "IB initialization failed (%d).\n", r); |
4192,11 → 5408,11 |
return r; |
} |
// r = radeon_vm_manager_init(rdev); |
// if (r) { |
// dev_err(rdev->dev, "vm manager initialization failed (%d).\n", r); |
// return r; |
// } |
r = radeon_vm_manager_init(rdev); |
if (r) { |
dev_err(rdev->dev, "vm manager initialization failed (%d).\n", r); |
return r; |
} |
return 0; |
} |
4240,6 → 5456,8 |
DRM_INFO("GPU not posted. posting now...\n"); |
atom_asic_init(rdev->mode_info.atom_context); |
} |
/* init golden registers */ |
si_init_golden_registers(rdev); |
/* Initialize scratch registers */ |
si_scratch_init(rdev); |
/* Initialize surface registers */ |
4261,10 → 5479,6 |
if (r) |
return r; |
r = radeon_irq_kms_init(rdev); |
if (r) |
return r; |
ring = &rdev->ring[RADEON_RING_TYPE_GFX_INDEX]; |
ring->ring_obj = NULL; |
r600_ring_init(rdev, ring, 1024 * 1024); |
4321,7 → 5535,7 |
} |
/** |
* si_get_gpu_clock - return GPU clock counter snapshot |
* si_get_gpu_clock_counter - return GPU clock counter snapshot |
* |
* @rdev: radeon_device pointer |
* |
4328,7 → 5542,7 |
* Fetches a GPU clock counter snapshot (SI). |
* Returns the 64 bit clock counter snapshot. |
*/ |
uint64_t si_get_gpu_clock(struct radeon_device *rdev) |
uint64_t si_get_gpu_clock_counter(struct radeon_device *rdev) |
{ |
uint64_t clock; |
4339,3 → 5553,96 |
mutex_unlock(&rdev->gpu_clock_mutex); |
return clock; |
} |
#if 0 |
int si_set_uvd_clocks(struct radeon_device *rdev, u32 vclk, u32 dclk) |
{ |
unsigned fb_div = 0, vclk_div = 0, dclk_div = 0; |
int r; |
/* bypass vclk and dclk with bclk */ |
WREG32_P(CG_UPLL_FUNC_CNTL_2, |
VCLK_SRC_SEL(1) | DCLK_SRC_SEL(1), |
~(VCLK_SRC_SEL_MASK | DCLK_SRC_SEL_MASK)); |
/* put PLL in bypass mode */ |
WREG32_P(CG_UPLL_FUNC_CNTL, UPLL_BYPASS_EN_MASK, ~UPLL_BYPASS_EN_MASK); |
if (!vclk || !dclk) { |
/* keep the Bypass mode, put PLL to sleep */ |
WREG32_P(CG_UPLL_FUNC_CNTL, UPLL_SLEEP_MASK, ~UPLL_SLEEP_MASK); |
return 0; |
} |
r = radeon_uvd_calc_upll_dividers(rdev, vclk, dclk, 125000, 250000, |
16384, 0x03FFFFFF, 0, 128, 5, |
&fb_div, &vclk_div, &dclk_div); |
if (r) |
return r; |
/* set RESET_ANTI_MUX to 0 */ |
WREG32_P(CG_UPLL_FUNC_CNTL_5, 0, ~RESET_ANTI_MUX_MASK); |
/* set VCO_MODE to 1 */ |
WREG32_P(CG_UPLL_FUNC_CNTL, UPLL_VCO_MODE_MASK, ~UPLL_VCO_MODE_MASK); |
/* toggle UPLL_SLEEP to 1 then back to 0 */ |
WREG32_P(CG_UPLL_FUNC_CNTL, UPLL_SLEEP_MASK, ~UPLL_SLEEP_MASK); |
WREG32_P(CG_UPLL_FUNC_CNTL, 0, ~UPLL_SLEEP_MASK); |
/* deassert UPLL_RESET */ |
WREG32_P(CG_UPLL_FUNC_CNTL, 0, ~UPLL_RESET_MASK); |
mdelay(1); |
r = radeon_uvd_send_upll_ctlreq(rdev, CG_UPLL_FUNC_CNTL); |
if (r) |
return r; |
/* assert UPLL_RESET again */ |
WREG32_P(CG_UPLL_FUNC_CNTL, UPLL_RESET_MASK, ~UPLL_RESET_MASK); |
/* disable spread spectrum. */ |
WREG32_P(CG_UPLL_SPREAD_SPECTRUM, 0, ~SSEN_MASK); |
/* set feedback divider */ |
WREG32_P(CG_UPLL_FUNC_CNTL_3, UPLL_FB_DIV(fb_div), ~UPLL_FB_DIV_MASK); |
/* set ref divider to 0 */ |
WREG32_P(CG_UPLL_FUNC_CNTL, 0, ~UPLL_REF_DIV_MASK); |
if (fb_div < 307200) |
WREG32_P(CG_UPLL_FUNC_CNTL_4, 0, ~UPLL_SPARE_ISPARE9); |
else |
WREG32_P(CG_UPLL_FUNC_CNTL_4, UPLL_SPARE_ISPARE9, ~UPLL_SPARE_ISPARE9); |
/* set PDIV_A and PDIV_B */ |
WREG32_P(CG_UPLL_FUNC_CNTL_2, |
UPLL_PDIV_A(vclk_div) | UPLL_PDIV_B(dclk_div), |
~(UPLL_PDIV_A_MASK | UPLL_PDIV_B_MASK)); |
/* give the PLL some time to settle */ |
mdelay(15); |
/* deassert PLL_RESET */ |
WREG32_P(CG_UPLL_FUNC_CNTL, 0, ~UPLL_RESET_MASK); |
mdelay(15); |
/* switch from bypass mode to normal mode */ |
WREG32_P(CG_UPLL_FUNC_CNTL, 0, ~UPLL_BYPASS_EN_MASK); |
r = radeon_uvd_send_upll_ctlreq(rdev, CG_UPLL_FUNC_CNTL); |
if (r) |
return r; |
/* switch VCLK and DCLK selection */ |
WREG32_P(CG_UPLL_FUNC_CNTL_2, |
VCLK_SRC_SEL(2) | DCLK_SRC_SEL(2), |
~(VCLK_SRC_SEL_MASK | DCLK_SRC_SEL_MASK)); |
mdelay(100); |
return 0; |
} |
#endif |
/drivers/video/drm/radeon/sid.h |
---|
28,7 → 28,37 |
#define TAHITI_GB_ADDR_CONFIG_GOLDEN 0x12011003 |
#define VERDE_GB_ADDR_CONFIG_GOLDEN 0x12010002 |
#define HAINAN_GB_ADDR_CONFIG_GOLDEN 0x02010001 |
/* discrete uvd clocks */ |
#define CG_UPLL_FUNC_CNTL 0x634 |
# define UPLL_RESET_MASK 0x00000001 |
# define UPLL_SLEEP_MASK 0x00000002 |
# define UPLL_BYPASS_EN_MASK 0x00000004 |
# define UPLL_CTLREQ_MASK 0x00000008 |
# define UPLL_VCO_MODE_MASK 0x00000600 |
# define UPLL_REF_DIV_MASK 0x003F0000 |
# define UPLL_CTLACK_MASK 0x40000000 |
# define UPLL_CTLACK2_MASK 0x80000000 |
#define CG_UPLL_FUNC_CNTL_2 0x638 |
# define UPLL_PDIV_A(x) ((x) << 0) |
# define UPLL_PDIV_A_MASK 0x0000007F |
# define UPLL_PDIV_B(x) ((x) << 8) |
# define UPLL_PDIV_B_MASK 0x00007F00 |
# define VCLK_SRC_SEL(x) ((x) << 20) |
# define VCLK_SRC_SEL_MASK 0x01F00000 |
# define DCLK_SRC_SEL(x) ((x) << 25) |
# define DCLK_SRC_SEL_MASK 0x3E000000 |
#define CG_UPLL_FUNC_CNTL_3 0x63C |
# define UPLL_FB_DIV(x) ((x) << 0) |
# define UPLL_FB_DIV_MASK 0x01FFFFFF |
#define CG_UPLL_FUNC_CNTL_4 0x644 |
# define UPLL_SPARE_ISPARE9 0x00020000 |
#define CG_UPLL_FUNC_CNTL_5 0x648 |
# define RESET_ANTI_MUX_MASK 0x00000200 |
#define CG_UPLL_SPREAD_SPECTRUM 0x650 |
# define SSEN_MASK 0x00000001 |
#define CG_MULT_THERMAL_STATUS 0x714 |
#define ASIC_MAX_TEMP(x) ((x) << 0) |
#define ASIC_MAX_TEMP_MASK 0x000001ff |
58,9 → 88,24 |
#define VGA_HDP_CONTROL 0x328 |
#define VGA_MEMORY_DISABLE (1 << 4) |
#define CG_CLKPIN_CNTL 0x660 |
# define XTALIN_DIVIDE (1 << 1) |
#define CG_CLKPIN_CNTL_2 0x664 |
# define MUX_TCLK_TO_XCLK (1 << 8) |
#define DMIF_ADDR_CONFIG 0xBD4 |
#define DMIF_ADDR_CALC 0xC00 |
#define SRBM_STATUS 0xE50 |
#define GRBM_RQ_PENDING (1 << 5) |
#define VMC_BUSY (1 << 8) |
#define MCB_BUSY (1 << 9) |
#define MCB_NON_DISPLAY_BUSY (1 << 10) |
#define MCC_BUSY (1 << 11) |
#define MCD_BUSY (1 << 12) |
#define SEM_BUSY (1 << 14) |
#define IH_BUSY (1 << 17) |
#define SRBM_SOFT_RESET 0x0E60 |
#define SOFT_RESET_BIF (1 << 1) |
81,6 → 126,10 |
#define CC_SYS_RB_BACKEND_DISABLE 0xe80 |
#define GC_USER_SYS_RB_BACKEND_DISABLE 0xe84 |
#define SRBM_STATUS2 0x0EC4 |
#define DMA_BUSY (1 << 5) |
#define DMA1_BUSY (1 << 6) |
#define VM_L2_CNTL 0x1400 |
#define ENABLE_L2_CACHE (1 << 0) |
#define ENABLE_L2_FRAGMENT_PROCESSING (1 << 1) |
781,18 → 830,18 |
# define THREAD_TRACE_FINISH (55 << 0) |
/* |
* UVD |
*/ |
#define UVD_UDEC_ADDR_CONFIG 0xEF4C |
#define UVD_UDEC_DB_ADDR_CONFIG 0xEF50 |
#define UVD_UDEC_DBW_ADDR_CONFIG 0xEF54 |
#define UVD_RBC_RB_RPTR 0xF690 |
#define UVD_RBC_RB_WPTR 0xF694 |
/* |
* PM4 |
*/ |
#define PACKET_TYPE0 0 |
#define PACKET_TYPE1 1 |
#define PACKET_TYPE2 2 |
#define PACKET_TYPE3 3 |
#define CP_PACKET_GET_TYPE(h) (((h) >> 30) & 3) |
#define CP_PACKET_GET_COUNT(h) (((h) >> 16) & 0x3FFF) |
#define CP_PACKET0_GET_REG(h) (((h) & 0xFFFF) << 2) |
#define CP_PACKET3_GET_OPCODE(h) (((h) >> 8) & 0xFF) |
#define PACKET0(reg, n) ((PACKET_TYPE0 << 30) | \ |
#define PACKET0(reg, n) ((RADEON_PACKET_TYPE0 << 30) | \ |
(((reg) >> 2) & 0xFFFF) | \ |
((n) & 0x3FFF) << 16) |
#define CP_PACKET2 0x80000000 |
801,7 → 850,7 |
#define PACKET2(v) (CP_PACKET2 | REG_SET(PACKET2_PAD, (v))) |
#define PACKET3(op, n) ((PACKET_TYPE3 << 30) | \ |
#define PACKET3(op, n) ((RADEON_PACKET_TYPE3 << 30) | \ |
(((op) & 0xFF) << 8) | \ |
((n) & 0x3FFF) << 16) |