summaryrefslogtreecommitdiff
path: root/shared-core
diff options
context:
space:
mode:
Diffstat (limited to 'shared-core')
-rw-r--r--shared-core/radeon_cp.c25
-rw-r--r--shared-core/radeon_drm.h9
-rw-r--r--shared-core/radeon_drv.h51
-rw-r--r--shared-core/radeon_irq.c20
4 files changed, 94 insertions, 11 deletions
diff --git a/shared-core/radeon_cp.c b/shared-core/radeon_cp.c
index 06861381..006d04f3 100644
--- a/shared-core/radeon_cp.c
+++ b/shared-core/radeon_cp.c
@@ -1390,6 +1390,28 @@ static void radeon_set_pcigart(drm_radeon_private_t * dev_priv, int on)
}
}
+void radeon_gart_flush(struct drm_device *dev)
+{
+ drm_radeon_private_t *dev_priv = dev->dev_private;
+
+ if (dev_priv->flags & RADEON_IS_IGPGART) {
+ RADEON_READ_IGPGART(dev_priv, RADEON_IGPGART_FLUSH);
+ RADEON_WRITE_IGPGART(RADEON_IGPGART_FLUSH, 0x1);
+ RADEON_READ_IGPGART(dev_priv, RADEON_IGPGART_FLUSH);
+ RADEON_WRITE_IGPGART(RADEON_IGPGART_FLUSH, 0x0);
+ } else if (dev_priv->flags & RADEON_IS_PCIE) {
+ u32 tmp = RADEON_READ_PCIE(dev_priv, RADEON_PCIE_TX_GART_CNTL);
+ tmp |= RADEON_PCIE_TX_GART_INVALIDATE_TLB;
+ RADEON_WRITE_PCIE(RADEON_PCIE_TX_GART_CNTL, tmp);
+ tmp &= ~RADEON_PCIE_TX_GART_INVALIDATE_TLB;
+ RADEON_WRITE_PCIE(RADEON_PCIE_TX_GART_CNTL, tmp);
+ } else {
+
+
+ }
+
+}
+
static int radeon_do_init_cp(struct drm_device * dev, drm_radeon_init_t * init)
{
drm_radeon_private_t *dev_priv = dev->dev_private;
@@ -2301,6 +2323,9 @@ int radeon_driver_firstopen(struct drm_device *dev)
if (ret != 0)
return ret;
+#ifdef RADEON_HAVE_BUFFER
+ drm_bo_driver_init(dev);
+#endif
return 0;
}
diff --git a/shared-core/radeon_drm.h b/shared-core/radeon_drm.h
index b0ef702b..913b23c5 100644
--- a/shared-core/radeon_drm.h
+++ b/shared-core/radeon_drm.h
@@ -434,8 +434,17 @@ typedef struct {
int pfCurrentPage; /* which buffer is being displayed? */
int crtc2_base; /* CRTC2 frame offset */
int tiling_enabled; /* set by drm, read by 2d + 3d clients */
+
+ unsigned int last_fence;
} drm_radeon_sarea_t;
+/* The only fence class we support */
+#define DRM_RADEON_FENCE_CLASS_ACCEL 0
+/* Fence type that guarantees read-write flush */
+#define DRM_RADEON_FENCE_TYPE_RW 2
+/* cache flushes programmed just before the fence */
+#define DRM_RADEON_FENCE_FLAG_FLUSHED 0x01000000
+
/* WARNING: If you change any of these defines, make sure to change the
* defines in the Xserver file (xf86drmRadeon.h)
*
diff --git a/shared-core/radeon_drv.h b/shared-core/radeon_drv.h
index 006559df..f74fe933 100644
--- a/shared-core/radeon_drv.h
+++ b/shared-core/radeon_drv.h
@@ -104,6 +104,11 @@
#define DRIVER_MINOR 28
#define DRIVER_PATCHLEVEL 0
+#if defined(__linux__)
+#define RADEON_HAVE_FENCE
+#define RADEON_HAVE_BUFFER
+#endif
+
/*
* Radeon chip families
*/
@@ -284,8 +289,9 @@ typedef struct drm_radeon_private {
struct mem_block *fb_heap;
/* SW interrupt */
- wait_queue_head_t swi_queue;
- atomic_t swi_emitted;
+ wait_queue_head_t irq_queue;
+ int counter;
+
int vblank_crtc;
uint32_t irq_enable_reg;
int irq_enabled;
@@ -344,6 +350,7 @@ extern int radeon_cp_resume(struct drm_device *dev, void *data, struct drm_file
extern int radeon_engine_reset(struct drm_device *dev, void *data, struct drm_file *file_priv);
extern int radeon_fullscreen(struct drm_device *dev, void *data, struct drm_file *file_priv);
extern int radeon_cp_buffers(struct drm_device *dev, void *data, struct drm_file *file_priv);
+extern void radeon_gart_flush(struct drm_device *dev);
extern void radeon_freelist_reset(struct drm_device * dev);
extern struct drm_buf *radeon_freelist_get(struct drm_device * dev);
@@ -362,6 +369,7 @@ extern void radeon_mem_release(struct drm_file *file_priv,
/* radeon_irq.c */
extern int radeon_irq_emit(struct drm_device *dev, void *data, struct drm_file *file_priv);
extern int radeon_irq_wait(struct drm_device *dev, void *data, struct drm_file *file_priv);
+extern int radeon_emit_irq(struct drm_device * dev);
extern void radeon_do_release(struct drm_device * dev);
extern int radeon_driver_vblank_wait(struct drm_device * dev,
@@ -395,6 +403,30 @@ extern int r300_do_cp_cmdbuf(struct drm_device *dev,
struct drm_file *file_priv,
drm_radeon_kcmd_buffer_t* cmdbuf);
+
+#ifdef RADEON_HAVE_FENCE
+/* i915_fence.c */
+
+
+extern void radeon_fence_handler(struct drm_device *dev);
+extern int radeon_fence_emit_sequence(struct drm_device *dev, uint32_t class,
+ uint32_t flags, uint32_t *sequence,
+ uint32_t *native_type);
+extern void radeon_poke_flush(struct drm_device *dev, uint32_t class);
+extern int radeon_fence_has_irq(struct drm_device *dev, uint32_t class, uint32_t flags);
+#endif
+
+#ifdef RADEON_HAVE_BUFFER
+/* radeon_buffer.c */
+extern drm_ttm_backend_t *radeon_create_ttm_backend_entry(struct drm_device *dev);
+extern int radeon_fence_types(struct drm_buffer_object *bo, uint32_t *class, uint32_t *type);
+extern int radeon_invalidate_caches(struct drm_device *dev, uint64_t buffer_flags);
+extern uint32_t radeon_evict_mask(struct drm_buffer_object *bo);
+extern int radeon_init_mem_type(struct drm_device * dev, uint32_t type,
+ struct drm_mem_type_manager * man);
+extern int radeon_move(struct drm_buffer_object * bo,
+ int evict, int no_wait, struct drm_bo_mem_reg * new_mem);
+#endif
/* Flags for stats.boxes
*/
#define RADEON_BOX_DMA_IDLE 0x1
@@ -1266,4 +1298,19 @@ do { \
write &= mask; \
} while (0)
+/* Breadcrumb - swi irq */
+#define READ_BREADCRUMB(dev_priv) RADEON_READ(RADEON_LAST_SWI_REG)
+
+static inline int radeon_update_breadcrumb(struct drm_device *dev)
+{
+ drm_radeon_private_t *dev_priv = dev->dev_private;
+
+ dev_priv->sarea_priv->last_fence = ++dev_priv->counter;
+
+ if (dev_priv->counter > 0x7FFFFFFFUL)
+ dev_priv->sarea_priv->last_fence = dev_priv->counter = 1;
+
+ return dev_priv->counter;
+}
+
#endif /* __RADEON_DRV_H__ */
diff --git a/shared-core/radeon_irq.c b/shared-core/radeon_irq.c
index 1ece6399..3162e266 100644
--- a/shared-core/radeon_irq.c
+++ b/shared-core/radeon_irq.c
@@ -82,7 +82,10 @@ irqreturn_t radeon_driver_irq_handler(DRM_IRQ_ARGS)
/* SW interrupt */
if (stat & RADEON_SW_INT_TEST) {
- DRM_WAKEUP(&dev_priv->swi_queue);
+ DRM_WAKEUP(&dev_priv->irq_queue);
+#ifdef RADEON_HAVE_FENCE
+ radeon_fence_handler(dev);
+#endif
}
/* VBLANK interrupt */
@@ -109,14 +112,13 @@ irqreturn_t radeon_driver_irq_handler(DRM_IRQ_ARGS)
return IRQ_HANDLED;
}
-static int radeon_emit_irq(struct drm_device * dev)
+int radeon_emit_irq(struct drm_device * dev)
{
drm_radeon_private_t *dev_priv = dev->dev_private;
unsigned int ret;
RING_LOCALS;
- atomic_inc(&dev_priv->swi_emitted);
- ret = atomic_read(&dev_priv->swi_emitted);
+ ret = radeon_update_breadcrumb(dev);
BEGIN_RING(4);
OUT_RING_REG(RADEON_LAST_SWI_REG, ret);
@@ -133,13 +135,13 @@ static int radeon_wait_irq(struct drm_device * dev, int swi_nr)
(drm_radeon_private_t *) dev->dev_private;
int ret = 0;
- if (RADEON_READ(RADEON_LAST_SWI_REG) >= swi_nr)
+ if (READ_BREADCRUMB(dev_priv) >= swi_nr)
return 0;
dev_priv->stats.boxes |= RADEON_BOX_WAIT_IDLE;
- DRM_WAIT_ON(ret, dev_priv->swi_queue, 3 * DRM_HZ,
- RADEON_READ(RADEON_LAST_SWI_REG) >= swi_nr);
+ DRM_WAIT_ON(ret, dev_priv->irq_queue, 3 * DRM_HZ,
+ READ_BREADCRUMB(dev_priv) >= swi_nr);
return ret;
}
@@ -271,8 +273,8 @@ void radeon_driver_irq_postinstall(struct drm_device * dev)
drm_radeon_private_t *dev_priv =
(drm_radeon_private_t *) dev->dev_private;
- atomic_set(&dev_priv->swi_emitted, 0);
- DRM_INIT_WAITQUEUE(&dev_priv->swi_queue);
+ dev_priv->counter = 0;
+ DRM_INIT_WAITQUEUE(&dev_priv->irq_queue);
radeon_enable_interrupt(dev);
}