i965: Move device info initialization to common code
[mesa.git] / src / mesa / drivers / dri / r200 / r200_ioctl.c
index 6560efdca390bbd4defbce4d4080fa4973ee4abe..90232d45e9eb338244375e047362ce0e0829c0aa 100644 (file)
@@ -29,7 +29,7 @@ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
 
 /*
  * Authors:
- *   Keith Whitwell <keith@tungstengraphics.com>
+ *   Keith Whitwell <keithw@vmware.com>
  */
 
 #include <sched.h>
@@ -44,355 +44,40 @@ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
 
 
 #include "radeon_common.h"
-#include "radeon_lock.h"
 #include "r200_context.h"
-#include "r200_state.h"
 #include "r200_ioctl.h"
-#include "r200_tcl.h"
-#include "r200_sanity.h"
 #include "radeon_reg.h"
 
-#include "drirenderbuffer.h"
-#include "vblank.h"
-
 #define R200_TIMEOUT             512
 #define R200_IDLE_RETRY           16
 
-static void r200UserClear(GLcontext *ctx, GLuint mask)
-{
-   radeon_clear_tris(ctx, mask);
-}
-
-static void r200KernelClear(GLcontext *ctx, GLuint flags)
-{
-   r200ContextPtr rmesa = R200_CONTEXT(ctx);
-   __DRIdrawablePrivate *dPriv = radeon_get_drawable(&rmesa->radeon);
-   GLint cx, cy, cw, ch, ret;
-   GLuint i;
-
-   LOCK_HARDWARE( &rmesa->radeon );
-
-   /* Throttle the number of clear ioctls we do.
-    */
-   while ( 1 ) {
-      drm_radeon_getparam_t gp;
-      int ret;
-      int clear;
-
-      gp.param = RADEON_PARAM_LAST_CLEAR;
-      gp.value = (int *)&clear;
-      ret = drmCommandWriteRead( rmesa->radeon.dri.fd,
-                     DRM_RADEON_GETPARAM, &gp, sizeof(gp) );
-
-      if ( ret ) {
-        fprintf( stderr, "%s: drmRadeonGetParam: %d\n", __FUNCTION__, ret );
-        exit(1);
-      }
-
-      /* Clear throttling needs more thought.
-       */
-      if ( rmesa->radeon.sarea->last_clear - clear <= 25 ) {
-        break;
-      }
-
-      if (rmesa->radeon.do_usleeps) {
-        UNLOCK_HARDWARE( &rmesa->radeon );
-        DO_USLEEP( 1 );
-        LOCK_HARDWARE( &rmesa->radeon );
-      }
-   }
-
-   /* Send current state to the hardware */
-   rcommonFlushCmdBufLocked( &rmesa->radeon, __FUNCTION__ );
-
-
-  /* compute region after locking: */
-   cx = ctx->DrawBuffer->_Xmin;
-   cy = ctx->DrawBuffer->_Ymin;
-   cw = ctx->DrawBuffer->_Xmax - cx;
-   ch = ctx->DrawBuffer->_Ymax - cy;
-
-   /* Flip top to bottom */
-   cx += dPriv->x;
-   cy  = dPriv->y + dPriv->h - cy - ch;
-   for ( i = 0 ; i < dPriv->numClipRects ; ) {
-      GLint nr = MIN2( i + RADEON_NR_SAREA_CLIPRECTS, dPriv->numClipRects );
-      drm_clip_rect_t *box = dPriv->pClipRects;
-      drm_clip_rect_t *b = rmesa->radeon.sarea->boxes;
-      drm_radeon_clear_t clear;
-      drm_radeon_clear_rect_t depth_boxes[RADEON_NR_SAREA_CLIPRECTS];
-      GLint n = 0;
-
-      if (cw != dPriv->w || ch != dPriv->h) {
-         /* clear subregion */
-        for ( ; i < nr ; i++ ) {
-           GLint x = box[i].x1;
-           GLint y = box[i].y1;
-           GLint w = box[i].x2 - x;
-           GLint h = box[i].y2 - y;
-
-           if ( x < cx ) w -= cx - x, x = cx;
-           if ( y < cy ) h -= cy - y, y = cy;
-           if ( x + w > cx + cw ) w = cx + cw - x;
-           if ( y + h > cy + ch ) h = cy + ch - y;
-           if ( w <= 0 ) continue;
-           if ( h <= 0 ) continue;
-
-           b->x1 = x;
-           b->y1 = y;
-           b->x2 = x + w;
-           b->y2 = y + h;
-           b++;
-           n++;
-        }
-      } else {
-         /* clear whole window */
-        for ( ; i < nr ; i++ ) {
-           *b++ = box[i];
-           n++;
-        }
-      }
-
-      rmesa->radeon.sarea->nbox = n;
-
-      clear.flags       = flags;
-      clear.clear_color = rmesa->radeon.state.color.clear;
-      clear.clear_depth = rmesa->radeon.state.depth.clear;     /* needed for hyperz */
-      clear.color_mask  = rmesa->hw.msk.cmd[MSK_RB3D_PLANEMASK];
-      clear.depth_mask  = rmesa->radeon.state.stencil.clear;
-      clear.depth_boxes = depth_boxes;
-
-      n--;
-      b = rmesa->radeon.sarea->boxes;
-      for ( ; n >= 0 ; n-- ) {
-        depth_boxes[n].f[CLEAR_X1] = (float)b[n].x1;
-        depth_boxes[n].f[CLEAR_Y1] = (float)b[n].y1;
-        depth_boxes[n].f[CLEAR_X2] = (float)b[n].x2;
-        depth_boxes[n].f[CLEAR_Y2] = (float)b[n].y2;
-        depth_boxes[n].f[CLEAR_DEPTH] = ctx->Depth.Clear;
-      }
-
-      ret = drmCommandWrite( rmesa->radeon.dri.fd, DRM_RADEON_CLEAR,
-                            &clear, sizeof(clear));
-
-
-      if ( ret ) {
-        UNLOCK_HARDWARE( &rmesa->radeon );
-        fprintf( stderr, "DRM_RADEON_CLEAR: return = %d\n", ret );
-        exit( 1 );
-      }
-   }
-   UNLOCK_HARDWARE( &rmesa->radeon );
-}
 /* ================================================================
  * Buffer clear
  */
-static void r200Clear( GLcontext *ctx, GLbitfield mask )
+static void r200Clear( struct gl_context *ctx, GLbitfield mask )
 {
-   r200ContextPtr rmesa = R200_CONTEXT(ctx);
-   __DRIdrawablePrivate *dPriv = radeon_get_drawable(&rmesa->radeon);
-   GLuint flags = 0;
-   GLuint color_mask = 0;
-   GLuint orig_mask = mask;
-
-   if ( R200_DEBUG & DEBUG_IOCTL ) {
-          if (rmesa->radeon.sarea)
-              fprintf( stderr, "r200Clear %x %d\n", mask, rmesa->radeon.sarea->pfCurrentPage);
-          else
-              fprintf( stderr, "r200Clear %x radeon->sarea is NULL\n", mask);
-   }
-
-   {
-      LOCK_HARDWARE( &rmesa->radeon );
-      UNLOCK_HARDWARE( &rmesa->radeon );
-      if ( dPriv->numClipRects == 0 )
-        return;
-   }
+   GLuint hwmask, swmask;
+   GLuint hwbits = BUFFER_BIT_FRONT_LEFT | BUFFER_BIT_BACK_LEFT |
+                   BUFFER_BIT_DEPTH | BUFFER_BIT_STENCIL |
+                   BUFFER_BIT_COLOR0;
 
    radeonFlush( ctx );
 
-   if ( mask & BUFFER_BIT_FRONT_LEFT ) {
-      flags |= RADEON_FRONT;
-      color_mask = rmesa->hw.msk.cmd[MSK_RB3D_PLANEMASK];
-      mask &= ~BUFFER_BIT_FRONT_LEFT;
-   }
-
-   if ( mask & BUFFER_BIT_BACK_LEFT ) {
-      flags |= RADEON_BACK;
-      color_mask = rmesa->hw.msk.cmd[MSK_RB3D_PLANEMASK];
-      mask &= ~BUFFER_BIT_BACK_LEFT;
-   }
-
-   if ( mask & BUFFER_BIT_DEPTH ) {
-      flags |= RADEON_DEPTH;
-      mask &= ~BUFFER_BIT_DEPTH;
-   }
-
-   if ( (mask & BUFFER_BIT_STENCIL) ) {
-      flags |= RADEON_STENCIL;
-      mask &= ~BUFFER_BIT_STENCIL;
-   }
-
-   if ( mask ) {
-      if (R200_DEBUG & DEBUG_FALLBACKS)
-        fprintf(stderr, "%s: swrast clear, mask: %x\n", __FUNCTION__, mask);
-      _swrast_Clear( ctx, mask );
-   }
-
-   if ( !flags )
-      return;
-
-   if (rmesa->using_hyperz) {
-      flags |= RADEON_USE_COMP_ZBUF;
-/*      if (rmesa->radeon.radeonScreen->chip_family == CHIP_FAMILY_R200)
-        flags |= RADEON_USE_HIERZ; */
-      if (!((flags & RADEON_DEPTH) && (flags & RADEON_STENCIL) &&
-           ((rmesa->radeon.state.stencil.clear & R200_STENCIL_WRITE_MASK) == R200_STENCIL_WRITE_MASK))) {
-         flags |= RADEON_CLEAR_FASTZ;
-      }
-   }
-
-   if (rmesa->radeon.radeonScreen->kernel_mm)
-      r200UserClear(ctx, orig_mask);
-   else {
-      r200KernelClear(ctx, flags);
-      rmesa->radeon.hw.all_dirty = GL_TRUE;
-   }
-}
-
-/* This version of AllocateMemoryMESA allocates only GART memory, and
- * only does so after the point at which the driver has been
- * initialized.
- *
- * Theoretically a valid context isn't required.  However, in this
- * implementation, it is, as I'm using the hardware lock to protect
- * the kernel data structures, and the current context to get the
- * device fd.
- */
-void *r200AllocateMemoryMESA(__DRIscreen *screen, GLsizei size,
-                            GLfloat readfreq, GLfloat writefreq,
-                            GLfloat priority)
-{
-   GET_CURRENT_CONTEXT(ctx);
-   r200ContextPtr rmesa;
-   int region_offset;
-   drm_radeon_mem_alloc_t alloc;
-   int ret;
-
-   if (R200_DEBUG & DEBUG_IOCTL)
-      fprintf(stderr, "%s sz %d %f/%f/%f\n", __FUNCTION__, size, readfreq,
-             writefreq, priority);
-
-   if (!ctx || !(rmesa = R200_CONTEXT(ctx)) || !rmesa->radeon.radeonScreen->gartTextures.map)
-      return NULL;
-
-   if (getenv("R200_NO_ALLOC"))
-      return NULL;
-
-   alloc.region = RADEON_MEM_REGION_GART;
-   alloc.alignment = 0;
-   alloc.size = size;
-   alloc.region_offset = &region_offset;
-
-   ret = drmCommandWriteRead( rmesa->radeon.radeonScreen->driScreen->fd,
-                             DRM_RADEON_ALLOC,
-                             &alloc, sizeof(alloc));
+   hwmask = mask & hwbits;
+   swmask = mask & ~hwbits;
 
-   if (ret) {
-      fprintf(stderr, "%s: DRM_RADEON_ALLOC ret %d\n", __FUNCTION__, ret);
-      return NULL;
+   if ( swmask ) {
+      if (R200_DEBUG & RADEON_FALLBACKS)
+        fprintf(stderr, "%s: swrast clear, mask: %x\n", __func__, swmask);
+      _swrast_Clear( ctx, swmask );
    }
 
-   {
-      char *region_start = (char *)rmesa->radeon.radeonScreen->gartTextures.map;
-      return (void *)(region_start + region_offset);
-   }
-}
-
-
-/* Called via glXFreeMemoryMESA() */
-void r200FreeMemoryMESA(__DRIscreen *screen, GLvoid *pointer)
-{
-   GET_CURRENT_CONTEXT(ctx);
-   r200ContextPtr rmesa;
-   ptrdiff_t region_offset;
-   drm_radeon_mem_free_t memfree;
-   int ret;
-
-   if (R200_DEBUG & DEBUG_IOCTL)
-      fprintf(stderr, "%s %p\n", __FUNCTION__, pointer);
-
-   if (!ctx || !(rmesa = R200_CONTEXT(ctx)) || !rmesa->radeon.radeonScreen->gartTextures.map) {
-      fprintf(stderr, "%s: no context\n", __FUNCTION__);
-      return;
-   }
-
-   region_offset = (char *)pointer - (char *)rmesa->radeon.radeonScreen->gartTextures.map;
-
-   if (region_offset < 0 ||
-       region_offset > rmesa->radeon.radeonScreen->gartTextures.size) {
-      fprintf(stderr, "offset %d outside range 0..%d\n", region_offset,
-             rmesa->radeon.radeonScreen->gartTextures.size);
+   if ( !hwmask )
       return;
-   }
-
-   memfree.region = RADEON_MEM_REGION_GART;
-   memfree.region_offset = region_offset;
-
-   ret = drmCommandWrite( rmesa->radeon.radeonScreen->driScreen->fd,
-                         DRM_RADEON_FREE,
-                         &memfree, sizeof(memfree));
-
-   if (ret)
-      fprintf(stderr, "%s: DRM_RADEON_FREE ret %d\n", __FUNCTION__, ret);
-}
-
-/* Called via glXGetMemoryOffsetMESA() */
-GLuint r200GetMemoryOffsetMESA(__DRIscreen *screen, const GLvoid *pointer)
-{
-   GET_CURRENT_CONTEXT(ctx);
-   r200ContextPtr rmesa;
-   GLuint card_offset;
-
-   if (!ctx || !(rmesa = R200_CONTEXT(ctx)) ) {
-      fprintf(stderr, "%s: no context\n", __FUNCTION__);
-      return ~0;
-   }
-
-   if (!r200IsGartMemory( rmesa, pointer, 0 ))
-      return ~0;
-
-   card_offset = r200GartOffsetFromVirtual( rmesa, pointer );
 
-   return card_offset - rmesa->radeon.radeonScreen->gart_base;
+   radeonUserClear(ctx, hwmask);
 }
 
-GLboolean r200IsGartMemory( r200ContextPtr rmesa, const GLvoid *pointer,
-                          GLint size )
-{
-   ptrdiff_t offset = (char *)pointer - (char *)rmesa->radeon.radeonScreen->gartTextures.map;
-   int valid = (size >= 0 &&
-               offset >= 0 &&
-               offset + size < rmesa->radeon.radeonScreen->gartTextures.size);
-
-   if (R200_DEBUG & DEBUG_IOCTL)
-      fprintf(stderr, "r200IsGartMemory( %p ) : %d\n", pointer, valid );
-
-   return valid;
-}
-
-
-GLuint r200GartOffsetFromVirtual( r200ContextPtr rmesa, const GLvoid *pointer )
-{
-   ptrdiff_t offset = (char *)pointer - (char *)rmesa->radeon.radeonScreen->gartTextures.map;
-
-   if (offset < 0 || offset > rmesa->radeon.radeonScreen->gartTextures.size)
-      return ~0;
-   else
-      return rmesa->radeon.radeonScreen->gart_texture_offset + offset;
-}
-
-
 
 void r200InitIoctlFuncs( struct dd_function_table *functions )
 {