diff options
author | Keith Whitwell <keith@tungstengraphics.com> | 2002-09-21 14:20:53 +0000 |
---|---|---|
committer | Keith Whitwell <keith@tungstengraphics.com> | 2002-09-21 14:20:53 +0000 |
commit | 61ed1d25859ebbaaf88f3d35864263fee36c373b (patch) | |
tree | e9f8574b25ab3c6fb74fa352ee773cfc79d3d343 | |
parent | 698c795d4f80d934358393e3d8985f642ed295b5 (diff) |
wait commands for cmdbuffer ioctl
-rw-r--r-- | shared-core/radeon_drm.h | 6 | ||||
-rw-r--r-- | shared-core/radeon_drv.h | 2 | ||||
-rw-r--r-- | shared-core/radeon_state.c | 71 | ||||
-rw-r--r-- | shared/radeon.h | 12 | ||||
-rw-r--r-- | shared/radeon_drm.h | 6 | ||||
-rw-r--r-- | shared/radeon_drv.h | 2 | ||||
-rw-r--r-- | shared/radeon_state.c | 71 |
7 files changed, 133 insertions, 37 deletions
diff --git a/shared-core/radeon_drm.h b/shared-core/radeon_drm.h index 1977dd44..8a4d8174 100644 --- a/shared-core/radeon_drm.h +++ b/shared-core/radeon_drm.h @@ -164,8 +164,14 @@ typedef union { struct { unsigned char cmd_type, buf_idx, pad0, pad1; } dma; + struct { + unsigned char cmd_type, flags, pad0, pad1; + } wait; } drm_radeon_cmd_header_t; +#define RADEON_WAIT_2D 0x1 +#define RADEON_WAIT_3D 0x2 + #define RADEON_FRONT 0x1 #define RADEON_BACK 0x2 diff --git a/shared-core/radeon_drv.h b/shared-core/radeon_drv.h index 49ab1b93..4e43c5c2 100644 --- a/shared-core/radeon_drv.h +++ b/shared-core/radeon_drv.h @@ -567,6 +567,8 @@ extern int radeon_emit_irq(drm_device_t *dev); #define RADEON_TXFORMAT_ARGB4444 5 #define RADEON_TXFORMAT_ARGB8888 6 #define RADEON_TXFORMAT_RGBA8888 7 +#define RADEON_TXFORMAT_VYUY422 10 +#define RADEON_TXFORMAT_YVYU422 11 #define R200_PP_TXCBLEND_0 0x2f00 #define R200_PP_TXCBLEND_1 0x2f10 diff --git a/shared-core/radeon_state.c b/shared-core/radeon_state.c index f1084ccd..5f3c8b01 100644 --- a/shared-core/radeon_state.c +++ b/shared-core/radeon_state.c @@ -1087,6 +1087,8 @@ static int radeon_cp_dispatch_texture( drm_device_t *dev, case RADEON_TXFORMAT_ARGB1555: case RADEON_TXFORMAT_RGB565: case RADEON_TXFORMAT_ARGB4444: + case RADEON_TXFORMAT_VYUY422: + case RADEON_TXFORMAT_YVYU422: format = RADEON_COLOR_FORMAT_RGB565; tex_width = tex->width * 2; blit_width = image->width * 2; @@ -1381,7 +1383,7 @@ int radeon_cp_vertex( DRM_IOCTL_ARGS ) LOCK_TEST_WITH_RETURN( dev ); if ( !dev_priv ) { - DRM_ERROR( "%s called with no initialization\n", __func__ ); + DRM_ERROR( "%s called with no initialization\n", __FUNCTION__ ); return DRM_ERR(EINVAL); } @@ -1468,7 +1470,7 @@ int radeon_cp_indices( DRM_IOCTL_ARGS ) LOCK_TEST_WITH_RETURN( dev ); if ( !dev_priv ) { - DRM_ERROR( "%s called with no initialization\n", __func__ ); + DRM_ERROR( "%s called with no initialization\n", __FUNCTION__ ); return DRM_ERR(EINVAL); } @@ -1618,7 +1620,7 @@ int radeon_cp_indirect( DRM_IOCTL_ARGS ) LOCK_TEST_WITH_RETURN( dev ); if ( !dev_priv ) { - DRM_ERROR( "%s called with no initialization\n", __func__ ); + DRM_ERROR( "%s called with no initialization\n", __FUNCTION__ ); return DRM_ERR(EINVAL); } @@ -1695,7 +1697,7 @@ int radeon_cp_vertex2( DRM_IOCTL_ARGS ) LOCK_TEST_WITH_RETURN( dev ); if ( !dev_priv ) { - DRM_ERROR( "%s called with no initialization\n", __func__ ); + DRM_ERROR( "%s called with no initialization\n", __FUNCTION__ ); return DRM_ERR(EINVAL); } @@ -1939,14 +1941,18 @@ static int radeon_emit_packet3_cliprect( drm_device_t *dev, if ( i < cmdbuf->nbox ) { if (DRM_COPY_FROM_USER_UNCHECKED( &box, &boxes[i], sizeof(box) )) return DRM_ERR(EFAULT); - /* FIXME The second and subsequent times round this loop, send a - * WAIT_UNTIL_3D_IDLE before calling emit_clip_rect(). This - * fixes a lockup on fast machines when sending several - * cliprects with a cmdbuf, as when waving a 2D window over - * a 3D window. Something in the commands from user space - * seems to hang the card when they're sent several times - * in a row. That would be the correct place to fix it but - * this works around it until I can figure that out - Tim Smith */ + /* FIXME The second and subsequent times round + * this loop, send a WAIT_UNTIL_3D_IDLE before + * calling emit_clip_rect(). This fixes a + * lockup on fast machines when sending + * several cliprects with a cmdbuf, as when + * waving a 2D window over a 3D + * window. Something in the commands from user + * space seems to hang the card when they're + * sent several times in a row. That would be + * the correct place to fix it but this works + * around it until I can figure that out - Tim + * Smith */ if ( i ) { BEGIN_RING( 2 ); RADEON_WAIT_UNTIL_3D_IDLE(); @@ -1970,6 +1976,34 @@ static int radeon_emit_packet3_cliprect( drm_device_t *dev, } +static int radeon_emit_wait( drm_device_t *dev, int flags ) +{ + drm_radeon_private_t *dev_priv = dev->dev_private; + RING_LOCALS; + + DRM_DEBUG("%s: %x\n", __FUNCTION__, flags); + switch (flags) { + case RADEON_WAIT_2D: + BEGIN_RING( 2 ); + RADEON_WAIT_UNTIL_2D_IDLE(); + ADVANCE_RING(); + break; + case RADEON_WAIT_3D: + BEGIN_RING( 2 ); + RADEON_WAIT_UNTIL_3D_IDLE(); + ADVANCE_RING(); + break; + case RADEON_WAIT_2D|RADEON_WAIT_3D: + BEGIN_RING( 2 ); + RADEON_WAIT_UNTIL_IDLE(); + ADVANCE_RING(); + break; + default: + return DRM_ERR(EINVAL); + } + + return 0; +} int radeon_cp_cmdbuf( DRM_IOCTL_ARGS ) { @@ -1985,14 +2019,13 @@ int radeon_cp_cmdbuf( DRM_IOCTL_ARGS ) LOCK_TEST_WITH_RETURN( dev ); if ( !dev_priv ) { - DRM_ERROR( "%s called with no initialization\n", __func__ ); + DRM_ERROR( "%s called with no initialization\n", __FUNCTION__ ); return DRM_ERR(EINVAL); } DRM_COPY_FROM_USER_IOCTL( cmdbuf, (drm_radeon_cmd_buffer_t *)data, sizeof(cmdbuf) ); - DRM_DEBUG( "pid=%d\n", DRM_CURRENTPID ); RING_SPACE_TEST_WITH_RETURN( dev_priv ); VB_AGE_TEST_WITH_RETURN( dev_priv ); @@ -2083,6 +2116,14 @@ int radeon_cp_cmdbuf( DRM_IOCTL_ARGS ) return DRM_ERR(EINVAL); } break; + + case RADEON_CMD_WAIT: + DRM_DEBUG("RADEON_CMD_WAIT\n"); + if (radeon_emit_wait( dev, header.wait.flags )) { + DRM_ERROR("radeon_emit_wait failed\n"); + return DRM_ERR(EINVAL); + } + break; default: DRM_ERROR("bad cmd_type %d at %p\n", header.header.cmd_type, @@ -2107,7 +2148,7 @@ int radeon_cp_getparam( DRM_IOCTL_ARGS ) int value; if ( !dev_priv ) { - DRM_ERROR( "%s called with no initialization\n", __func__ ); + DRM_ERROR( "%s called with no initialization\n", __FUNCTION__ ); return DRM_ERR(EINVAL); } diff --git a/shared/radeon.h b/shared/radeon.h index bab7b81f..ff5bad97 100644 --- a/shared/radeon.h +++ b/shared/radeon.h @@ -149,13 +149,11 @@ RADEON_WRITE( RADEON_GEN_INT_CNTL, 0 ); \ } while (0) -/* #ifdef __linux__ */ -/* #define IWH(x) init_waitqueue_head(x) */ -/* #else */ -/* #define IWH(x) */ -/* #endif */ - -#define IWH(x) +#ifdef __linux__ +#define IWH(x) init_waitqueue_head(x) +#else +#define IWH(x) +#endif #define DRIVER_POSTINSTALL() do { \ drm_radeon_private_t *dev_priv = \ diff --git a/shared/radeon_drm.h b/shared/radeon_drm.h index 1977dd44..8a4d8174 100644 --- a/shared/radeon_drm.h +++ b/shared/radeon_drm.h @@ -164,8 +164,14 @@ typedef union { struct { unsigned char cmd_type, buf_idx, pad0, pad1; } dma; + struct { + unsigned char cmd_type, flags, pad0, pad1; + } wait; } drm_radeon_cmd_header_t; +#define RADEON_WAIT_2D 0x1 +#define RADEON_WAIT_3D 0x2 + #define RADEON_FRONT 0x1 #define RADEON_BACK 0x2 diff --git a/shared/radeon_drv.h b/shared/radeon_drv.h index 49ab1b93..4e43c5c2 100644 --- a/shared/radeon_drv.h +++ b/shared/radeon_drv.h @@ -567,6 +567,8 @@ extern int radeon_emit_irq(drm_device_t *dev); #define RADEON_TXFORMAT_ARGB4444 5 #define RADEON_TXFORMAT_ARGB8888 6 #define RADEON_TXFORMAT_RGBA8888 7 +#define RADEON_TXFORMAT_VYUY422 10 +#define RADEON_TXFORMAT_YVYU422 11 #define R200_PP_TXCBLEND_0 0x2f00 #define R200_PP_TXCBLEND_1 0x2f10 diff --git a/shared/radeon_state.c b/shared/radeon_state.c index f1084ccd..5f3c8b01 100644 --- a/shared/radeon_state.c +++ b/shared/radeon_state.c @@ -1087,6 +1087,8 @@ static int radeon_cp_dispatch_texture( drm_device_t *dev, case RADEON_TXFORMAT_ARGB1555: case RADEON_TXFORMAT_RGB565: case RADEON_TXFORMAT_ARGB4444: + case RADEON_TXFORMAT_VYUY422: + case RADEON_TXFORMAT_YVYU422: format = RADEON_COLOR_FORMAT_RGB565; tex_width = tex->width * 2; blit_width = image->width * 2; @@ -1381,7 +1383,7 @@ int radeon_cp_vertex( DRM_IOCTL_ARGS ) LOCK_TEST_WITH_RETURN( dev ); if ( !dev_priv ) { - DRM_ERROR( "%s called with no initialization\n", __func__ ); + DRM_ERROR( "%s called with no initialization\n", __FUNCTION__ ); return DRM_ERR(EINVAL); } @@ -1468,7 +1470,7 @@ int radeon_cp_indices( DRM_IOCTL_ARGS ) LOCK_TEST_WITH_RETURN( dev ); if ( !dev_priv ) { - DRM_ERROR( "%s called with no initialization\n", __func__ ); + DRM_ERROR( "%s called with no initialization\n", __FUNCTION__ ); return DRM_ERR(EINVAL); } @@ -1618,7 +1620,7 @@ int radeon_cp_indirect( DRM_IOCTL_ARGS ) LOCK_TEST_WITH_RETURN( dev ); if ( !dev_priv ) { - DRM_ERROR( "%s called with no initialization\n", __func__ ); + DRM_ERROR( "%s called with no initialization\n", __FUNCTION__ ); return DRM_ERR(EINVAL); } @@ -1695,7 +1697,7 @@ int radeon_cp_vertex2( DRM_IOCTL_ARGS ) LOCK_TEST_WITH_RETURN( dev ); if ( !dev_priv ) { - DRM_ERROR( "%s called with no initialization\n", __func__ ); + DRM_ERROR( "%s called with no initialization\n", __FUNCTION__ ); return DRM_ERR(EINVAL); } @@ -1939,14 +1941,18 @@ static int radeon_emit_packet3_cliprect( drm_device_t *dev, if ( i < cmdbuf->nbox ) { if (DRM_COPY_FROM_USER_UNCHECKED( &box, &boxes[i], sizeof(box) )) return DRM_ERR(EFAULT); - /* FIXME The second and subsequent times round this loop, send a - * WAIT_UNTIL_3D_IDLE before calling emit_clip_rect(). This - * fixes a lockup on fast machines when sending several - * cliprects with a cmdbuf, as when waving a 2D window over - * a 3D window. Something in the commands from user space - * seems to hang the card when they're sent several times - * in a row. That would be the correct place to fix it but - * this works around it until I can figure that out - Tim Smith */ + /* FIXME The second and subsequent times round + * this loop, send a WAIT_UNTIL_3D_IDLE before + * calling emit_clip_rect(). This fixes a + * lockup on fast machines when sending + * several cliprects with a cmdbuf, as when + * waving a 2D window over a 3D + * window. Something in the commands from user + * space seems to hang the card when they're + * sent several times in a row. That would be + * the correct place to fix it but this works + * around it until I can figure that out - Tim + * Smith */ if ( i ) { BEGIN_RING( 2 ); RADEON_WAIT_UNTIL_3D_IDLE(); @@ -1970,6 +1976,34 @@ static int radeon_emit_packet3_cliprect( drm_device_t *dev, } +static int radeon_emit_wait( drm_device_t *dev, int flags ) +{ + drm_radeon_private_t *dev_priv = dev->dev_private; + RING_LOCALS; + + DRM_DEBUG("%s: %x\n", __FUNCTION__, flags); + switch (flags) { + case RADEON_WAIT_2D: + BEGIN_RING( 2 ); + RADEON_WAIT_UNTIL_2D_IDLE(); + ADVANCE_RING(); + break; + case RADEON_WAIT_3D: + BEGIN_RING( 2 ); + RADEON_WAIT_UNTIL_3D_IDLE(); + ADVANCE_RING(); + break; + case RADEON_WAIT_2D|RADEON_WAIT_3D: + BEGIN_RING( 2 ); + RADEON_WAIT_UNTIL_IDLE(); + ADVANCE_RING(); + break; + default: + return DRM_ERR(EINVAL); + } + + return 0; +} int radeon_cp_cmdbuf( DRM_IOCTL_ARGS ) { @@ -1985,14 +2019,13 @@ int radeon_cp_cmdbuf( DRM_IOCTL_ARGS ) LOCK_TEST_WITH_RETURN( dev ); if ( !dev_priv ) { - DRM_ERROR( "%s called with no initialization\n", __func__ ); + DRM_ERROR( "%s called with no initialization\n", __FUNCTION__ ); return DRM_ERR(EINVAL); } DRM_COPY_FROM_USER_IOCTL( cmdbuf, (drm_radeon_cmd_buffer_t *)data, sizeof(cmdbuf) ); - DRM_DEBUG( "pid=%d\n", DRM_CURRENTPID ); RING_SPACE_TEST_WITH_RETURN( dev_priv ); VB_AGE_TEST_WITH_RETURN( dev_priv ); @@ -2083,6 +2116,14 @@ int radeon_cp_cmdbuf( DRM_IOCTL_ARGS ) return DRM_ERR(EINVAL); } break; + + case RADEON_CMD_WAIT: + DRM_DEBUG("RADEON_CMD_WAIT\n"); + if (radeon_emit_wait( dev, header.wait.flags )) { + DRM_ERROR("radeon_emit_wait failed\n"); + return DRM_ERR(EINVAL); + } + break; default: DRM_ERROR("bad cmd_type %d at %p\n", header.header.cmd_type, @@ -2107,7 +2148,7 @@ int radeon_cp_getparam( DRM_IOCTL_ARGS ) int value; if ( !dev_priv ) { - DRM_ERROR( "%s called with no initialization\n", __func__ ); + DRM_ERROR( "%s called with no initialization\n", __FUNCTION__ ); return DRM_ERR(EINVAL); } |