On Sunday 29 May 2005 02:31, Ben Skeggs wrote:
> Morning,
> 
> After playing UT2004 for 10 or so minutes, and then quickly checking 
> some other
> apps known to worn, I see no regressions with either patch.
> 
> I'll be putting it through some more rigorous testing as the day 
> progresses, will
> report back if I find anything.
> 
> Also, out of interest, what triggered the lockup you saw?

Pretty much anything could trigger it, from glxgears (unlikely lockup) over 
glean (regular lockups) to cube (almost instant lockup).

Unfortunately, just like others are reporting, I'm still getting lockups, 
too. This time, however, they are more elusive as the lockups disappear as 
soon as I start looking for them:

I used the attached patch (in variations) to hunt for the previous lockup. 
What this patch does is that it basically commits the ring buffer after 
every ADVANCE_RING and waits for the read ptr to catch up with the write 
ptr. Feel free to try this patch if you're seeing lockups, perhaps you can 
find something out that way. However, as soon as I enable the call to 
commit_and_wait, the lockups disappear for me.

I'm still going to try to find this thing, but it looks like it's going to 
be difficult.

cu,
Nicolai
Index: drm/shared-core/radeon_cp.c
===================================================================
RCS file: /cvsroot/r300/r300_driver/drm/shared-core/radeon_cp.c,v
retrieving revision 1.7
diff -u -3 -p -r1.7 radeon_cp.c
--- drm/shared-core/radeon_cp.c	19 Apr 2005 21:05:18 -0000	1.7
+++ drm/shared-core/radeon_cp.c	28 May 2005 20:34:04 -0000
@@ -923,6 +923,56 @@ static int radeon_do_wait_for_idle(drm_r
 	return DRM_ERR(EBUSY);
 }

+
+/* Debugging function:
+ *
+ * Commit the ring immediately and verify that the hardware is making
+ * progress on the ring.
+ */
+static int failed_once = 0;
+static const char* prev_inflight_caller = 0;
+static const char* prev2_inflight_caller = 0;
+static const char* prev3_inflight_caller = 0;
+
+void radeon_do_inflight_commit_and_wait(drm_radeon_private_t * dev_priv, const char* caller)
+{
+	const char* prev3_caller = prev3_inflight_caller;
+	const char* prev2_caller = prev2_inflight_caller;
+	const char* prev_caller = prev_inflight_caller;
+	const char* cur_caller = caller;
+	u32 old_tail = RADEON_READ(RADEON_CP_RB_WPTR);
+	u32 new_tail = dev_priv->ring.tail;
+	int i;
+
+	prev3_inflight_caller = prev2_caller;
+	prev2_inflight_caller = prev_caller;
+	prev_inflight_caller = caller;
+
+	if (failed_once)
+		return;
+
+	COMMIT_RING();
+
+	for(i = 0; i < dev_priv->usec_timeout; i++) {
+		u32 head = GET_RING_HEAD(dev_priv);
+
+		if (new_tail > old_tail) {
+			if (head > old_tail && head <= new_tail)
+				return;
+		} else {
+			if (head <= new_tail || head > old_tail)
+				return;
+		}
+
+		DRM_UDELAY(1);
+	}
+
+	DRM_ERROR("failed! (caller = %s, prev = %s <- %s <- %s)\n", cur_caller, prev_caller, prev2_caller, prev3_caller);
+	radeon_status(dev_priv);
+	failed_once = 1;
+}
+
+
 /* ================================================================
  * CP control, initialization
  */
Index: drm/shared-core/radeon_drv.h
===================================================================
RCS file: /cvsroot/r300/r300_driver/drm/shared-core/radeon_drv.h,v
retrieving revision 1.12
diff -u -3 -p -r1.12 radeon_drv.h
--- drm/shared-core/radeon_drv.h	3 Mar 2005 04:40:21 -0000	1.12
+++ drm/shared-core/radeon_drv.h	28 May 2005 20:34:05 -0000
@@ -985,14 +985,39 @@ do {									\

 #define RING_LOCALS	int write, _nr; unsigned int mask; u32 *ring;

+#define ALIGN_RING() do {						\
+	int _nr = 32 - (dev_priv->ring.tail & 31);			\
+	int _write;							\
+	if (dev_priv->ring.space <= (_nr+1) * sizeof(u32)) {		\
+		COMMIT_RING();						\
+		radeon_wait_ring( dev_priv, (_nr+1) * sizeof(u32) );	\
+	}								\
+	_write = dev_priv->ring.tail;					\
+	if (_write & 1)	{						\
+		dev_priv->ring.start[_write++] = RADEON_CP_PACKET2;	\
+		_write = _write % dev_priv->ring.tail_mask;		\
+		_nr--;							\
+	}								\
+	while( _nr >= 2 ) {						\
+		/*dev_priv->ring.start[_write++] = CP_PACKET3( RADEON_CP_NOP, 0 );*/ \
+		/*dev_priv->ring.start[_write++] = CP_PACKET0( 0x1438, 0 );*/ \
+		dev_priv->ring.start[_write++] = RADEON_CP_PACKET2; 	\
+		dev_priv->ring.start[_write++] = RADEON_CP_PACKET2; 	\
+		_write = _write % dev_priv->ring.tail_mask;		\
+		_nr -= 2;						\
+	}								\
+	dev_priv->ring.tail = _write;					\
+} while (0)
+
 #define BEGIN_RING( n ) do {						\
+	ALIGN_RING(); /* TEST TEST */					\
 	if ( RADEON_VERBOSE ) {						\
 		DRM_INFO( "BEGIN_RING( %d ) in %s\n",			\
 			   n, __FUNCTION__ );				\
 	}								\
-	if ( dev_priv->ring.space <= (n) * sizeof(u32) ) {		\
+	if ( dev_priv->ring.space <= dev_priv->ring.size/2 /*(n+1) * sizeof(u32)*/ ) {		\
                 COMMIT_RING();						\
-		radeon_wait_ring( dev_priv, (n) * sizeof(u32) );	\
+		radeon_wait_ring( dev_priv, dev_priv->ring.size/2/*(n+1) * sizeof(u32)*/ );	\
 	}								\
 	_nr = n; dev_priv->ring.space -= (n) * sizeof(u32);		\
 	ring = dev_priv->ring.start;					\
@@ -1000,6 +1025,8 @@ do {									\
 	mask = dev_priv->ring.tail_mask;				\
 } while (0)

+void radeon_do_inflight_commit_and_wait(drm_radeon_private_t * dev_priv, const char* caller);
+
 #define ADVANCE_RING() do {						\
 	if ( RADEON_VERBOSE ) {						\
 		DRM_INFO( "ADVANCE_RING() wr=0x%06x tail=0x%06x\n",	\
@@ -1012,12 +1039,17 @@ do {									\
 			write, __LINE__);						\
 	} else								\
 		dev_priv->ring.tail = write;				\
+									\
+	radeon_do_inflight_commit_and_wait(dev_priv, __FUNCTION__);	\
 } while (0)

 #define COMMIT_RING() do {						\
 	/* Flush writes to ring */					\
 	DRM_MEMORYBARRIER();						\
-	GET_RING_HEAD( dev_priv );					\
+	u32 head = RADEON_READ( RADEON_CP_RB_RPTR );			\
+	u32 tail = RADEON_READ( RADEON_CP_RB_WPTR );			\
+	if (tail != dev_priv->ring.tail && head == dev_priv->ring.tail)	\
+		DRM_ERROR("head == tail\n");				\
 	RADEON_WRITE( RADEON_CP_RB_WPTR, dev_priv->ring.tail );		\
 	/* read from PCI bus to ensure correct posting */		\
 	RADEON_READ( RADEON_CP_RB_RPTR );				\

Attachment: pgpnOiYsFiBh5.pgp
Description: PGP signature

Reply via email to