Commit 1ec14ad3 authored by Chris Wilson's avatar Chris Wilson
Browse files

drm/i915: Implement GPU semaphores for inter-ring synchronisation on SNB



The bulk of the change is to convert the growing list of rings into an
array so that the relationship between the rings and the semaphore sync
registers can be easily computed.
Signed-off-by: default avatarChris Wilson <chris@chris-wilson.co.uk>
parent 340479aa
......@@ -339,10 +339,10 @@ static int i915_gem_request_info(struct seq_file *m, void *data)
return ret;
count = 0;
if (!list_empty(&dev_priv->render_ring.request_list)) {
if (!list_empty(&dev_priv->ring[RCS].request_list)) {
seq_printf(m, "Render requests:\n");
list_for_each_entry(gem_request,
&dev_priv->render_ring.request_list,
&dev_priv->ring[RCS].request_list,
list) {
seq_printf(m, " %d @ %d\n",
gem_request->seqno,
......@@ -350,10 +350,10 @@ static int i915_gem_request_info(struct seq_file *m, void *data)
}
count++;
}
if (!list_empty(&dev_priv->bsd_ring.request_list)) {
if (!list_empty(&dev_priv->ring[VCS].request_list)) {
seq_printf(m, "BSD requests:\n");
list_for_each_entry(gem_request,
&dev_priv->bsd_ring.request_list,
&dev_priv->ring[VCS].request_list,
list) {
seq_printf(m, " %d @ %d\n",
gem_request->seqno,
......@@ -361,10 +361,10 @@ static int i915_gem_request_info(struct seq_file *m, void *data)
}
count++;
}
if (!list_empty(&dev_priv->blt_ring.request_list)) {
if (!list_empty(&dev_priv->ring[BCS].request_list)) {
seq_printf(m, "BLT requests:\n");
list_for_each_entry(gem_request,
&dev_priv->blt_ring.request_list,
&dev_priv->ring[BCS].request_list,
list) {
seq_printf(m, " %d @ %d\n",
gem_request->seqno,
......@@ -398,15 +398,14 @@ static int i915_gem_seqno_info(struct seq_file *m, void *data)
struct drm_info_node *node = (struct drm_info_node *) m->private;
struct drm_device *dev = node->minor->dev;
drm_i915_private_t *dev_priv = dev->dev_private;
int ret;
int ret, i;
ret = mutex_lock_interruptible(&dev->struct_mutex);
if (ret)
return ret;
i915_ring_seqno_info(m, &dev_priv->render_ring);
i915_ring_seqno_info(m, &dev_priv->bsd_ring);
i915_ring_seqno_info(m, &dev_priv->blt_ring);
for (i = 0; i < I915_NUM_RINGS; i++)
i915_ring_seqno_info(m, &dev_priv->ring[i]);
mutex_unlock(&dev->struct_mutex);
......@@ -419,7 +418,7 @@ static int i915_interrupt_info(struct seq_file *m, void *data)
struct drm_info_node *node = (struct drm_info_node *) m->private;
struct drm_device *dev = node->minor->dev;
drm_i915_private_t *dev_priv = dev->dev_private;
int ret;
int ret, i;
ret = mutex_lock_interruptible(&dev->struct_mutex);
if (ret)
......@@ -458,9 +457,8 @@ static int i915_interrupt_info(struct seq_file *m, void *data)
}
seq_printf(m, "Interrupts received: %d\n",
atomic_read(&dev_priv->irq_received));
i915_ring_seqno_info(m, &dev_priv->render_ring);
i915_ring_seqno_info(m, &dev_priv->bsd_ring);
i915_ring_seqno_info(m, &dev_priv->blt_ring);
for (i = 0; i < I915_NUM_RINGS; i++)
i915_ring_seqno_info(m, &dev_priv->ring[i]);
mutex_unlock(&dev->struct_mutex);
return 0;
......@@ -503,13 +501,7 @@ static int i915_hws_info(struct seq_file *m, void *data)
volatile u32 *hws;
int i;
switch ((uintptr_t)node->info_ent->data) {
case RING_RENDER: ring = &dev_priv->render_ring; break;
case RING_BSD: ring = &dev_priv->bsd_ring; break;
case RING_BLT: ring = &dev_priv->blt_ring; break;
default: return -EINVAL;
}
ring = &dev_priv->ring[(uintptr_t)node->info_ent->data];
hws = (volatile u32 *)ring->status_page.page_addr;
if (hws == NULL)
return 0;
......@@ -569,17 +561,11 @@ static int i915_ringbuffer_data(struct seq_file *m, void *data)
struct intel_ring_buffer *ring;
int ret;
switch ((uintptr_t)node->info_ent->data) {
case RING_RENDER: ring = &dev_priv->render_ring; break;
case RING_BSD: ring = &dev_priv->bsd_ring; break;
case RING_BLT: ring = &dev_priv->blt_ring; break;
default: return -EINVAL;
}
ret = mutex_lock_interruptible(&dev->struct_mutex);
if (ret)
return ret;
ring = &dev_priv->ring[(uintptr_t)node->info_ent->data];
if (!ring->obj) {
seq_printf(m, "No ringbuffer setup\n");
} else {
......@@ -603,21 +589,20 @@ static int i915_ringbuffer_info(struct seq_file *m, void *data)
drm_i915_private_t *dev_priv = dev->dev_private;
struct intel_ring_buffer *ring;
switch ((uintptr_t)node->info_ent->data) {
case RING_RENDER: ring = &dev_priv->render_ring; break;
case RING_BSD: ring = &dev_priv->bsd_ring; break;
case RING_BLT: ring = &dev_priv->blt_ring; break;
default: return -EINVAL;
}
ring = &dev_priv->ring[(uintptr_t)node->info_ent->data];
if (ring->size == 0)
return 0;
return 0;
seq_printf(m, "Ring %s:\n", ring->name);
seq_printf(m, " Head : %08x\n", I915_READ_HEAD(ring) & HEAD_ADDR);
seq_printf(m, " Tail : %08x\n", I915_READ_TAIL(ring) & TAIL_ADDR);
seq_printf(m, " Size : %08x\n", ring->size);
seq_printf(m, " Active : %08x\n", intel_ring_get_active_head(ring));
seq_printf(m, " NOPID : %08x\n", I915_READ_NOPID(ring));
if (IS_GEN6(dev)) {
seq_printf(m, " Sync 0 : %08x\n", I915_READ_SYNC_0(ring));
seq_printf(m, " Sync 1 : %08x\n", I915_READ_SYNC_1(ring));
}
seq_printf(m, " Control : %08x\n", I915_READ_CTL(ring));
seq_printf(m, " Start : %08x\n", I915_READ_START(ring));
......@@ -1177,15 +1162,15 @@ static struct drm_info_list i915_debugfs_list[] = {
{"i915_gem_seqno", i915_gem_seqno_info, 0},
{"i915_gem_fence_regs", i915_gem_fence_regs_info, 0},
{"i915_gem_interrupt", i915_interrupt_info, 0},
{"i915_gem_hws", i915_hws_info, 0, (void *)RING_RENDER},
{"i915_gem_hws_blt", i915_hws_info, 0, (void *)RING_BLT},
{"i915_gem_hws_bsd", i915_hws_info, 0, (void *)RING_BSD},
{"i915_ringbuffer_data", i915_ringbuffer_data, 0, (void *)RING_RENDER},
{"i915_ringbuffer_info", i915_ringbuffer_info, 0, (void *)RING_RENDER},
{"i915_bsd_ringbuffer_data", i915_ringbuffer_data, 0, (void *)RING_BSD},
{"i915_bsd_ringbuffer_info", i915_ringbuffer_info, 0, (void *)RING_BSD},
{"i915_blt_ringbuffer_data", i915_ringbuffer_data, 0, (void *)RING_BLT},
{"i915_blt_ringbuffer_info", i915_ringbuffer_info, 0, (void *)RING_BLT},
{"i915_gem_hws", i915_hws_info, 0, (void *)RCS},
{"i915_gem_hws_blt", i915_hws_info, 0, (void *)BCS},
{"i915_gem_hws_bsd", i915_hws_info, 0, (void *)VCS},
{"i915_ringbuffer_data", i915_ringbuffer_data, 0, (void *)RCS},
{"i915_ringbuffer_info", i915_ringbuffer_info, 0, (void *)RCS},
{"i915_bsd_ringbuffer_data", i915_ringbuffer_data, 0, (void *)VCS},
{"i915_bsd_ringbuffer_info", i915_ringbuffer_info, 0, (void *)VCS},
{"i915_blt_ringbuffer_data", i915_ringbuffer_data, 0, (void *)BCS},
{"i915_blt_ringbuffer_info", i915_ringbuffer_info, 0, (void *)BCS},
{"i915_batchbuffers", i915_batchbuffer_info, 0},
{"i915_error_state", i915_error_state, 0},
{"i915_rstdby_delays", i915_rstdby_delays, 0},
......
......@@ -49,6 +49,8 @@
static int i915_init_phys_hws(struct drm_device *dev)
{
drm_i915_private_t *dev_priv = dev->dev_private;
struct intel_ring_buffer *ring = LP_RING(dev_priv);
/* Program Hardware Status Page */
dev_priv->status_page_dmah =
drm_pci_alloc(dev, PAGE_SIZE, PAGE_SIZE);
......@@ -57,11 +59,10 @@ static int i915_init_phys_hws(struct drm_device *dev)
DRM_ERROR("Can not allocate hardware status page\n");
return -ENOMEM;
}
dev_priv->render_ring.status_page.page_addr
= dev_priv->status_page_dmah->vaddr;
ring->status_page.page_addr = dev_priv->status_page_dmah->vaddr;
dev_priv->dma_status_page = dev_priv->status_page_dmah->busaddr;
memset(dev_priv->render_ring.status_page.page_addr, 0, PAGE_SIZE);
memset(ring->status_page.page_addr, 0, PAGE_SIZE);
if (INTEL_INFO(dev)->gen >= 4)
dev_priv->dma_status_page |= (dev_priv->dma_status_page >> 28) &
......@@ -79,13 +80,15 @@ static int i915_init_phys_hws(struct drm_device *dev)
static void i915_free_hws(struct drm_device *dev)
{
drm_i915_private_t *dev_priv = dev->dev_private;
struct intel_ring_buffer *ring = LP_RING(dev_priv);
if (dev_priv->status_page_dmah) {
drm_pci_free(dev, dev_priv->status_page_dmah);
dev_priv->status_page_dmah = NULL;
}
if (dev_priv->render_ring.status_page.gfx_addr) {
dev_priv->render_ring.status_page.gfx_addr = 0;
if (ring->status_page.gfx_addr) {
ring->status_page.gfx_addr = 0;
drm_core_ioremapfree(&dev_priv->hws_map, dev);
}
......@@ -97,7 +100,7 @@ void i915_kernel_lost_context(struct drm_device * dev)
{
drm_i915_private_t *dev_priv = dev->dev_private;
struct drm_i915_master_private *master_priv;
struct intel_ring_buffer *ring = &dev_priv->render_ring;
struct intel_ring_buffer *ring = LP_RING(dev_priv);
/*
* We should never lose context on the ring with modesetting
......@@ -123,6 +126,8 @@ void i915_kernel_lost_context(struct drm_device * dev)
static int i915_dma_cleanup(struct drm_device * dev)
{
drm_i915_private_t *dev_priv = dev->dev_private;
int i;
/* Make sure interrupts are disabled here because the uninstall ioctl
* may not have been called from userspace and after dev_private
* is freed, it's too late.
......@@ -131,9 +136,8 @@ static int i915_dma_cleanup(struct drm_device * dev)
drm_irq_uninstall(dev);
mutex_lock(&dev->struct_mutex);
intel_cleanup_ring_buffer(&dev_priv->render_ring);
intel_cleanup_ring_buffer(&dev_priv->bsd_ring);
intel_cleanup_ring_buffer(&dev_priv->blt_ring);
for (i = 0; i < I915_NUM_RINGS; i++)
intel_cleanup_ring_buffer(&dev_priv->ring[i]);
mutex_unlock(&dev->struct_mutex);
/* Clear the HWS virtual address at teardown */
......@@ -147,6 +151,7 @@ static int i915_initialize(struct drm_device * dev, drm_i915_init_t * init)
{
drm_i915_private_t *dev_priv = dev->dev_private;
struct drm_i915_master_private *master_priv = dev->primary->master->driver_priv;
struct intel_ring_buffer *ring = LP_RING(dev_priv);
master_priv->sarea = drm_getsarea(dev);
if (master_priv->sarea) {
......@@ -157,24 +162,24 @@ static int i915_initialize(struct drm_device * dev, drm_i915_init_t * init)
}
if (init->ring_size != 0) {
if (dev_priv->render_ring.obj != NULL) {
if (ring->obj != NULL) {
i915_dma_cleanup(dev);
DRM_ERROR("Client tried to initialize ringbuffer in "
"GEM mode\n");
return -EINVAL;
}
dev_priv->render_ring.size = init->ring_size;
ring->size = init->ring_size;
dev_priv->render_ring.map.offset = init->ring_start;
dev_priv->render_ring.map.size = init->ring_size;
dev_priv->render_ring.map.type = 0;
dev_priv->render_ring.map.flags = 0;
dev_priv->render_ring.map.mtrr = 0;
ring->map.offset = init->ring_start;
ring->map.size = init->ring_size;
ring->map.type = 0;
ring->map.flags = 0;
ring->map.mtrr = 0;
drm_core_ioremap_wc(&dev_priv->render_ring.map, dev);
drm_core_ioremap_wc(&ring->map, dev);
if (dev_priv->render_ring.map.handle == NULL) {
if (ring->map.handle == NULL) {
i915_dma_cleanup(dev);
DRM_ERROR("can not ioremap virtual address for"
" ring buffer\n");
......@@ -182,7 +187,7 @@ static int i915_initialize(struct drm_device * dev, drm_i915_init_t * init)
}
}
dev_priv->render_ring.virtual_start = dev_priv->render_ring.map.handle;
ring->virtual_start = ring->map.handle;
dev_priv->cpp = init->cpp;
dev_priv->back_offset = init->back_offset;
......@@ -201,12 +206,10 @@ static int i915_initialize(struct drm_device * dev, drm_i915_init_t * init)
static int i915_dma_resume(struct drm_device * dev)
{
drm_i915_private_t *dev_priv = (drm_i915_private_t *) dev->dev_private;
struct intel_ring_buffer *ring = LP_RING(dev_priv);
struct intel_ring_buffer *ring;
DRM_DEBUG_DRIVER("%s\n", __func__);
ring = &dev_priv->render_ring;
if (ring->map.handle == NULL) {
DRM_ERROR("can not ioremap virtual address for"
" ring buffer\n");
......@@ -326,7 +329,7 @@ static int i915_emit_cmds(struct drm_device * dev, int *buffer, int dwords)
drm_i915_private_t *dev_priv = dev->dev_private;
int i, ret;
if ((dwords+1) * sizeof(int) >= dev_priv->render_ring.size - 8)
if ((dwords+1) * sizeof(int) >= LP_RING(dev_priv)->size - 8)
return -EINVAL;
for (i = 0; i < dwords;) {
......@@ -565,13 +568,12 @@ static int i915_dispatch_flip(struct drm_device * dev)
return 0;
}
static int i915_quiescent(struct drm_device * dev)
static int i915_quiescent(struct drm_device *dev)
{
drm_i915_private_t *dev_priv = dev->dev_private;
struct intel_ring_buffer *ring = LP_RING(dev->dev_private);
i915_kernel_lost_context(dev);
return intel_wait_ring_buffer(&dev_priv->render_ring,
dev_priv->render_ring.size - 8);
return intel_wait_ring_buffer(ring, ring->size - 8);
}
static int i915_flush_ioctl(struct drm_device *dev, void *data,
......@@ -828,7 +830,7 @@ static int i915_set_status_page(struct drm_device *dev, void *data,
{
drm_i915_private_t *dev_priv = dev->dev_private;
drm_i915_hws_addr_t *hws = data;
struct intel_ring_buffer *ring = &dev_priv->render_ring;
struct intel_ring_buffer *ring = LP_RING(dev_priv);
if (!I915_NEED_GFX_HWS(dev))
return -EINVAL;
......@@ -1978,7 +1980,7 @@ int i915_driver_load(struct drm_device *dev, unsigned long flags)
if (!IS_I945G(dev) && !IS_I945GM(dev))
pci_enable_msi(dev->pdev);
spin_lock_init(&dev_priv->user_irq_lock);
spin_lock_init(&dev_priv->irq_lock);
spin_lock_init(&dev_priv->error_lock);
dev_priv->trace_irq_seqno = 0;
......
......@@ -487,11 +487,11 @@ int i915_reset(struct drm_device *dev, u8 flags)
!dev_priv->mm.suspended) {
dev_priv->mm.suspended = 0;
dev_priv->render_ring.init(&dev_priv->render_ring);
dev_priv->ring[RCS].init(&dev_priv->ring[RCS]);
if (HAS_BSD(dev))
dev_priv->bsd_ring.init(&dev_priv->bsd_ring);
dev_priv->ring[VCS].init(&dev_priv->ring[VCS]);
if (HAS_BLT(dev))
dev_priv->blt_ring.init(&dev_priv->blt_ring);
dev_priv->ring[BCS].init(&dev_priv->ring[BCS]);
mutex_unlock(&dev->struct_mutex);
drm_irq_uninstall(dev);
......
......@@ -269,9 +269,7 @@ typedef struct drm_i915_private {
} *gmbus;
struct pci_dev *bridge_dev;
struct intel_ring_buffer render_ring;
struct intel_ring_buffer bsd_ring;
struct intel_ring_buffer blt_ring;
struct intel_ring_buffer ring[I915_NUM_RINGS];
uint32_t next_seqno;
drm_dma_handle_t *status_page_dmah;
......@@ -290,19 +288,15 @@ typedef struct drm_i915_private {
int page_flipping;
atomic_t irq_received;
/** Protects user_irq_refcount and irq_mask_reg */
spinlock_t user_irq_lock;
u32 trace_irq_seqno;
/* protects the irq masks */
spinlock_t irq_lock;
/** Cached value of IMR to avoid reads in updating the bitfield */
u32 irq_mask_reg;
u32 pipestat[2];
/** splitted irq regs for graphics and display engine on Ironlake,
irq_mask_reg is still used for display irq. */
u32 gt_irq_mask_reg;
u32 gt_irq_enable_reg;
u32 de_irq_enable_reg;
u32 pch_irq_mask_reg;
u32 pch_irq_enable_reg;
u32 irq_mask;
u32 gt_irq_mask;
u32 pch_irq_mask;
u32 hotplug_supported_mask;
struct work_struct hotplug_work;
......@@ -1104,7 +1098,8 @@ int __must_check i915_mutex_lock_interruptible(struct drm_device *dev);
int __must_check i915_gem_object_wait_rendering(struct drm_i915_gem_object *obj,
bool interruptible);
void i915_gem_object_move_to_active(struct drm_i915_gem_object *obj,
struct intel_ring_buffer *ring);
struct intel_ring_buffer *ring,
u32 seqno);
/**
* Returns true if seq1 is later than seq2.
......@@ -1272,6 +1267,17 @@ extern void intel_display_print_error_state(struct seq_file *m,
struct intel_display_error_state *error);
#endif
#define LP_RING(d) (&((struct drm_i915_private *)(d))->ring[RCS])
#define BEGIN_LP_RING(n) \
intel_ring_begin(LP_RING(dev_priv), (n))
#define OUT_RING(x) \
intel_ring_emit(LP_RING(dev_priv), x)
#define ADVANCE_LP_RING() \
intel_ring_advance(LP_RING(dev_priv))
/**
* Lock test for when it's just for synchronization of ring access.
*
......@@ -1279,8 +1285,7 @@ extern void intel_display_print_error_state(struct seq_file *m,
* has access to the ring.
*/
#define RING_LOCK_TEST_WITH_RETURN(dev, file) do { \
if (((drm_i915_private_t *)dev->dev_private)->render_ring.obj \
== NULL) \
if (LP_RING(dev->dev_private)->obj == NULL) \
LOCK_TEST_WITH_RETURN(dev, file); \
} while (0)
......@@ -1366,15 +1371,6 @@ i915_write(struct drm_i915_private *dev_priv, u32 reg, u64 val, int len)
}
}
#define BEGIN_LP_RING(n) \
intel_ring_begin(&dev_priv->render_ring, (n))
#define OUT_RING(x) \
intel_ring_emit(&dev_priv->render_ring, x)
#define ADVANCE_LP_RING() \
intel_ring_advance(&dev_priv->render_ring)
/**
* Reads a dword out of the status page, which is written to from the command
* queue by automatic updates, MI_REPORT_HEAD, MI_STORE_DATA_INDEX, or
......@@ -1391,7 +1387,7 @@ i915_write(struct drm_i915_private *dev_priv, u32 reg, u64 val, int len)
* The area from dword 0x20 to 0x3ff is available for driver usage.
*/
#define READ_HWSP(dev_priv, reg) (((volatile u32 *)\
(dev_priv->render_ring.status_page.page_addr))[reg])
(LP_RING(dev_priv)->status_page.page_addr))[reg])
#define READ_BREADCRUMB(dev_priv) READ_HWSP(dev_priv, I915_BREADCRUMB_INDEX)
#define I915_GEM_HWS_INDEX 0x20
#define I915_BREADCRUMB_INDEX 0x21
......
......@@ -1561,11 +1561,11 @@ i915_gem_object_put_pages_gtt(struct drm_i915_gem_object *obj)
void
i915_gem_object_move_to_active(struct drm_i915_gem_object *obj,
struct intel_ring_buffer *ring)
struct intel_ring_buffer *ring,
u32 seqno)
{
struct drm_device *dev = obj->base.dev;
struct drm_i915_private *dev_priv = dev->dev_private;
uint32_t seqno = i915_gem_next_request_seqno(dev, ring);
BUG_ON(ring == NULL);
obj->ring = ring;
......@@ -1679,7 +1679,8 @@ i915_gem_process_flushing_list(struct drm_device *dev,
obj->base.write_domain = 0;
list_del_init(&obj->gpu_write_list);
i915_gem_object_move_to_active(obj, ring);
i915_gem_object_move_to_active(obj, ring,
i915_gem_next_request_seqno(dev, ring));
trace_i915_gem_object_change_domain(obj,
obj->base.read_domains,
......@@ -1804,10 +1805,10 @@ void i915_gem_reset(struct drm_device *dev)
{
struct drm_i915_private *dev_priv = dev->dev_private;
struct drm_i915_gem_object *obj;
int i;
i915_gem_reset_ring_lists(dev_priv, &dev_priv->render_ring);
i915_gem_reset_ring_lists(dev_priv, &dev_priv->bsd_ring);
i915_gem_reset_ring_lists(dev_priv, &dev_priv->blt_ring);
for (i = 0; i < I915_NUM_RINGS; i++)
i915_gem_reset_ring_lists(dev_priv, &dev_priv->ring[i]);
/* Remove anything from the flushing lists. The GPU cache is likely
* to be lost on reset along with the data, so simply move the
......@@ -1846,6 +1847,7 @@ i915_gem_retire_requests_ring(struct drm_device *dev,
{
drm_i915_private_t *dev_priv = dev->dev_private;
uint32_t seqno;
int i;
if (!ring->status_page.page_addr ||
list_empty(&ring->request_list))
......@@ -1854,6 +1856,11 @@ i915_gem_retire_requests_ring(struct drm_device *dev,
WARN_ON(i915_verify_lists(dev));
seqno = ring->get_seqno(ring);
for (i = 0; i < I915_NUM_RINGS; i++)
if (seqno >= ring->sync_seqno[i])
ring->sync_seqno[i] = 0;
while (!list_empty(&ring->request_list)) {
struct drm_i915_gem_request *request;
......@@ -1892,7 +1899,7 @@ i915_gem_retire_requests_ring(struct drm_device *dev,
if (unlikely (dev_priv->trace_irq_seqno &&
i915_seqno_passed(dev_priv->trace_irq_seqno, seqno))) {
ring->user_irq_put(ring);
ring->irq_put(ring);
dev_priv->trace_irq_seqno = 0;
}
......@@ -1903,6 +1910,7 @@ void
i915_gem_retire_requests(struct drm_device *dev)
{
drm_i915_private_t *dev_priv = dev->dev_private;
int i;
if (!list_empty(&dev_priv->mm.deferred_free_list)) {
struct drm_i915_gem_object *obj, *next;
......@@ -1918,9 +1926,8 @@ i915_gem_retire_requests(struct drm_device *dev)
i915_gem_free_object_tail(obj);
}
i915_gem_retire_requests_ring(dev, &dev_priv->render_ring);
i915_gem_retire_requests_ring(dev, &dev_priv->bsd_ring);
i915_gem_retire_requests_ring(dev, &dev_priv->blt_ring);
for (i = 0; i < I915_NUM_RINGS; i++)
i915_gem_retire_requests_ring(dev, &dev_priv->ring[i]);
}
static void
......@@ -1942,9 +1949,9 @@ i915_gem_retire_work_handler(struct work_struct *work)
i915_gem_retire_requests(dev);
if (!dev_priv->mm.suspended &&
(!list_empty(&dev_priv->render_ring.request_list) ||
!list_empty(&dev_priv->bsd_ring.request_list) ||
!list_empty(&dev_priv->blt_ring.request_list)))
(!list_empty(&dev_priv->ring[RCS].request_list) ||
!list_empty(&dev_priv->ring[VCS].request_list) ||
!list_empty(&dev_priv->ring[BCS].request_list)))
queue_delayed_work(dev_priv->wq, &dev_priv->mm.retire_work, HZ);
mutex_unlock(&dev->struct_mutex);
}
......@@ -1993,7 +2000,7 @@ i915_do_wait_request(struct drm_device *dev, uint32_t seqno,
trace_i915_gem_request_wait_begin(dev, seqno);
ring->waiting_seqno = seqno;
ring->user_irq_get(ring);
ring->irq_get(ring);
if (interruptible)
ret = wait_event_interruptible(ring->irq_queue,
i915_seqno_passed(ring->get_seqno(ring), seqno)
......@@ -2003,7 +2010,7 @@ i915_do_wait_request(struct drm_device *dev, uint32_t seqno,
i915_seqno_passed(ring->get_seqno(ring), seqno)
|| atomic_read(&dev_priv->mm.wedged));
ring->user_irq_put(ring);
ring->irq_put(ring);
ring->waiting_seqno = 0;
trace_i915_gem_request_wait_end(dev, seqno);
......@@ -2159,7 +2166,7 @@ i915_gpu_idle(struct drm_device *dev)
{
drm_i915_private_t *dev_priv = dev->dev_private;
bool lists_empty;
int ret;
int ret, i;
lists_empty = (list_empty(&dev_priv->mm.flushing_list) &&
list_empty(&dev_priv->mm.active_list));
......@@ -2167,17 +2174,11 @@ i915_gpu_idle(struct drm_device *dev)
return 0;
/* Flush everything onto the inactive list. */
ret = i915_ring_idle(dev, &dev_priv->render_ring);
if (ret)
return ret;
ret = i915_ring_idle(dev, &dev_priv->bsd_ring);
if (ret)
return ret;
ret = i915_ring_idle(dev, &dev_priv->blt_ring);
if (ret)
return ret;
for (i = 0; i < I915_NUM_RINGS; i++) {
ret = i915_ring_idle(dev, &dev_priv->ring[i]);
if (ret)
return ret;
}
return 0;
}
......@@ -3153,11 +3154,11 @@ i915_gem_ring_throttle(struct drm_device *dev, struct drm_file *file)
* generation is designed to be run atomically and so is
* lockless.
*/
ring->user_irq_get(ring);
ring->irq_get(ring);
ret = wait_event_interruptible(ring->irq_queue,
i915_seqno_passed(ring->get_seqno(ring), seqno)
|| atomic_read(&dev_priv->mm.wedged));
ring->user_irq_put(ring);
ring->irq_put(ring);
if (ret == 0 && atomic_read(&dev_priv->mm.wedged))
ret = -EIO;
......@@ -3584,9 +3585,9 @@ i915_gem_init_ringbuffer(struct drm_device *dev)