The Design and Implementation of the FreeBSD Operating System, Second Edition
Now available: The Design and Implementation of the FreeBSD Operating System (Second Edition)


[ source navigation ] [ diff markup ] [ identifier search ] [ freetext search ] [ file search ] [ list types ] [ track identifier ]

FreeBSD/Linux Kernel Cross Reference
sys/dev/drm/r128_state.c

Version: -  FREEBSD  -  FREEBSD-13-STABLE  -  FREEBSD-13-0  -  FREEBSD-12-STABLE  -  FREEBSD-12-0  -  FREEBSD-11-STABLE  -  FREEBSD-11-0  -  FREEBSD-10-STABLE  -  FREEBSD-10-0  -  FREEBSD-9-STABLE  -  FREEBSD-9-0  -  FREEBSD-8-STABLE  -  FREEBSD-8-0  -  FREEBSD-7-STABLE  -  FREEBSD-7-0  -  FREEBSD-6-STABLE  -  FREEBSD-6-0  -  FREEBSD-5-STABLE  -  FREEBSD-5-0  -  FREEBSD-4-STABLE  -  FREEBSD-3-STABLE  -  FREEBSD22  -  l41  -  OPENBSD  -  linux-2.6  -  MK84  -  PLAN9  -  xnu-8792 
SearchContext: -  none  -  3  -  10 

    1 /* r128_state.c -- State support for r128 -*- linux-c -*-
    2  * Created: Thu Jan 27 02:53:43 2000 by gareth@valinux.com
    3  */
    4 /*-
    5  * Copyright 2000 VA Linux Systems, Inc., Sunnyvale, California.
    6  * All Rights Reserved.
    7  *
    8  * Permission is hereby granted, free of charge, to any person obtaining a
    9  * copy of this software and associated documentation files (the "Software"),
   10  * to deal in the Software without restriction, including without limitation
   11  * the rights to use, copy, modify, merge, publish, distribute, sublicense,
   12  * and/or sell copies of the Software, and to permit persons to whom the
   13  * Software is furnished to do so, subject to the following conditions:
   14  *
   15  * The above copyright notice and this permission notice (including the next
   16  * paragraph) shall be included in all copies or substantial portions of the
   17  * Software.
   18  *
   19  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
   20  * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
   21  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
   22  * PRECISION INSIGHT AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
   23  * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
   24  * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
   25  * DEALINGS IN THE SOFTWARE.
   26  *
   27  * Authors:
   28  *    Gareth Hughes <gareth@valinux.com>
   29  */
   30 
   31 #include <sys/cdefs.h>
   32 __FBSDID("$FreeBSD: releng/9.0/sys/dev/drm/r128_state.c 207066 2010-04-22 18:21:25Z rnoland $");
   33 
   34 #include "dev/drm/drmP.h"
   35 #include "dev/drm/drm.h"
   36 #include "dev/drm/r128_drm.h"
   37 #include "dev/drm/r128_drv.h"
   38 
   39 /* ================================================================
   40  * CCE hardware state programming functions
   41  */
   42 
   43 static void r128_emit_clip_rects(drm_r128_private_t * dev_priv,
   44                                  struct drm_clip_rect * boxes, int count)
   45 {
   46         u32 aux_sc_cntl = 0x00000000;
   47         RING_LOCALS;
   48         DRM_DEBUG("\n");
   49 
   50         BEGIN_RING((count < 3 ? count : 3) * 5 + 2);
   51 
   52         if (count >= 1) {
   53                 OUT_RING(CCE_PACKET0(R128_AUX1_SC_LEFT, 3));
   54                 OUT_RING(boxes[0].x1);
   55                 OUT_RING(boxes[0].x2 - 1);
   56                 OUT_RING(boxes[0].y1);
   57                 OUT_RING(boxes[0].y2 - 1);
   58 
   59                 aux_sc_cntl |= (R128_AUX1_SC_EN | R128_AUX1_SC_MODE_OR);
   60         }
   61         if (count >= 2) {
   62                 OUT_RING(CCE_PACKET0(R128_AUX2_SC_LEFT, 3));
   63                 OUT_RING(boxes[1].x1);
   64                 OUT_RING(boxes[1].x2 - 1);
   65                 OUT_RING(boxes[1].y1);
   66                 OUT_RING(boxes[1].y2 - 1);
   67 
   68                 aux_sc_cntl |= (R128_AUX2_SC_EN | R128_AUX2_SC_MODE_OR);
   69         }
   70         if (count >= 3) {
   71                 OUT_RING(CCE_PACKET0(R128_AUX3_SC_LEFT, 3));
   72                 OUT_RING(boxes[2].x1);
   73                 OUT_RING(boxes[2].x2 - 1);
   74                 OUT_RING(boxes[2].y1);
   75                 OUT_RING(boxes[2].y2 - 1);
   76 
   77                 aux_sc_cntl |= (R128_AUX3_SC_EN | R128_AUX3_SC_MODE_OR);
   78         }
   79 
   80         OUT_RING(CCE_PACKET0(R128_AUX_SC_CNTL, 0));
   81         OUT_RING(aux_sc_cntl);
   82 
   83         ADVANCE_RING();
   84 }
   85 
   86 static __inline__ void r128_emit_core(drm_r128_private_t * dev_priv)
   87 {
   88         drm_r128_sarea_t *sarea_priv = dev_priv->sarea_priv;
   89         drm_r128_context_regs_t *ctx = &sarea_priv->context_state;
   90         RING_LOCALS;
   91         DRM_DEBUG("\n");
   92 
   93         BEGIN_RING(2);
   94 
   95         OUT_RING(CCE_PACKET0(R128_SCALE_3D_CNTL, 0));
   96         OUT_RING(ctx->scale_3d_cntl);
   97 
   98         ADVANCE_RING();
   99 }
  100 
  101 static __inline__ void r128_emit_context(drm_r128_private_t * dev_priv)
  102 {
  103         drm_r128_sarea_t *sarea_priv = dev_priv->sarea_priv;
  104         drm_r128_context_regs_t *ctx = &sarea_priv->context_state;
  105         RING_LOCALS;
  106         DRM_DEBUG("\n");
  107 
  108         BEGIN_RING(13);
  109 
  110         OUT_RING(CCE_PACKET0(R128_DST_PITCH_OFFSET_C, 11));
  111         OUT_RING(ctx->dst_pitch_offset_c);
  112         OUT_RING(ctx->dp_gui_master_cntl_c);
  113         OUT_RING(ctx->sc_top_left_c);
  114         OUT_RING(ctx->sc_bottom_right_c);
  115         OUT_RING(ctx->z_offset_c);
  116         OUT_RING(ctx->z_pitch_c);
  117         OUT_RING(ctx->z_sten_cntl_c);
  118         OUT_RING(ctx->tex_cntl_c);
  119         OUT_RING(ctx->misc_3d_state_cntl_reg);
  120         OUT_RING(ctx->texture_clr_cmp_clr_c);
  121         OUT_RING(ctx->texture_clr_cmp_msk_c);
  122         OUT_RING(ctx->fog_color_c);
  123 
  124         ADVANCE_RING();
  125 }
  126 
  127 static __inline__ void r128_emit_setup(drm_r128_private_t * dev_priv)
  128 {
  129         drm_r128_sarea_t *sarea_priv = dev_priv->sarea_priv;
  130         drm_r128_context_regs_t *ctx = &sarea_priv->context_state;
  131         RING_LOCALS;
  132         DRM_DEBUG("\n");
  133 
  134         BEGIN_RING(3);
  135 
  136         OUT_RING(CCE_PACKET1(R128_SETUP_CNTL, R128_PM4_VC_FPU_SETUP));
  137         OUT_RING(ctx->setup_cntl);
  138         OUT_RING(ctx->pm4_vc_fpu_setup);
  139 
  140         ADVANCE_RING();
  141 }
  142 
  143 static __inline__ void r128_emit_masks(drm_r128_private_t * dev_priv)
  144 {
  145         drm_r128_sarea_t *sarea_priv = dev_priv->sarea_priv;
  146         drm_r128_context_regs_t *ctx = &sarea_priv->context_state;
  147         RING_LOCALS;
  148         DRM_DEBUG("\n");
  149 
  150         BEGIN_RING(5);
  151 
  152         OUT_RING(CCE_PACKET0(R128_DP_WRITE_MASK, 0));
  153         OUT_RING(ctx->dp_write_mask);
  154 
  155         OUT_RING(CCE_PACKET0(R128_STEN_REF_MASK_C, 1));
  156         OUT_RING(ctx->sten_ref_mask_c);
  157         OUT_RING(ctx->plane_3d_mask_c);
  158 
  159         ADVANCE_RING();
  160 }
  161 
  162 static __inline__ void r128_emit_window(drm_r128_private_t * dev_priv)
  163 {
  164         drm_r128_sarea_t *sarea_priv = dev_priv->sarea_priv;
  165         drm_r128_context_regs_t *ctx = &sarea_priv->context_state;
  166         RING_LOCALS;
  167         DRM_DEBUG("\n");
  168 
  169         BEGIN_RING(2);
  170 
  171         OUT_RING(CCE_PACKET0(R128_WINDOW_XY_OFFSET, 0));
  172         OUT_RING(ctx->window_xy_offset);
  173 
  174         ADVANCE_RING();
  175 }
  176 
  177 static __inline__ void r128_emit_tex0(drm_r128_private_t * dev_priv)
  178 {
  179         drm_r128_sarea_t *sarea_priv = dev_priv->sarea_priv;
  180         drm_r128_context_regs_t *ctx = &sarea_priv->context_state;
  181         drm_r128_texture_regs_t *tex = &sarea_priv->tex_state[0];
  182         int i;
  183         RING_LOCALS;
  184         DRM_DEBUG("\n");
  185 
  186         BEGIN_RING(7 + R128_MAX_TEXTURE_LEVELS);
  187 
  188         OUT_RING(CCE_PACKET0(R128_PRIM_TEX_CNTL_C,
  189                              2 + R128_MAX_TEXTURE_LEVELS));
  190         OUT_RING(tex->tex_cntl);
  191         OUT_RING(tex->tex_combine_cntl);
  192         OUT_RING(ctx->tex_size_pitch_c);
  193         for (i = 0; i < R128_MAX_TEXTURE_LEVELS; i++) {
  194                 OUT_RING(tex->tex_offset[i]);
  195         }
  196 
  197         OUT_RING(CCE_PACKET0(R128_CONSTANT_COLOR_C, 1));
  198         OUT_RING(ctx->constant_color_c);
  199         OUT_RING(tex->tex_border_color);
  200 
  201         ADVANCE_RING();
  202 }
  203 
  204 static __inline__ void r128_emit_tex1(drm_r128_private_t * dev_priv)
  205 {
  206         drm_r128_sarea_t *sarea_priv = dev_priv->sarea_priv;
  207         drm_r128_texture_regs_t *tex = &sarea_priv->tex_state[1];
  208         int i;
  209         RING_LOCALS;
  210         DRM_DEBUG("\n");
  211 
  212         BEGIN_RING(5 + R128_MAX_TEXTURE_LEVELS);
  213 
  214         OUT_RING(CCE_PACKET0(R128_SEC_TEX_CNTL_C, 1 + R128_MAX_TEXTURE_LEVELS));
  215         OUT_RING(tex->tex_cntl);
  216         OUT_RING(tex->tex_combine_cntl);
  217         for (i = 0; i < R128_MAX_TEXTURE_LEVELS; i++) {
  218                 OUT_RING(tex->tex_offset[i]);
  219         }
  220 
  221         OUT_RING(CCE_PACKET0(R128_SEC_TEXTURE_BORDER_COLOR_C, 0));
  222         OUT_RING(tex->tex_border_color);
  223 
  224         ADVANCE_RING();
  225 }
  226 
  227 static void r128_emit_state(drm_r128_private_t * dev_priv)
  228 {
  229         drm_r128_sarea_t *sarea_priv = dev_priv->sarea_priv;
  230         unsigned int dirty = sarea_priv->dirty;
  231 
  232         DRM_DEBUG("dirty=0x%08x\n", dirty);
  233 
  234         if (dirty & R128_UPLOAD_CORE) {
  235                 r128_emit_core(dev_priv);
  236                 sarea_priv->dirty &= ~R128_UPLOAD_CORE;
  237         }
  238 
  239         if (dirty & R128_UPLOAD_CONTEXT) {
  240                 r128_emit_context(dev_priv);
  241                 sarea_priv->dirty &= ~R128_UPLOAD_CONTEXT;
  242         }
  243 
  244         if (dirty & R128_UPLOAD_SETUP) {
  245                 r128_emit_setup(dev_priv);
  246                 sarea_priv->dirty &= ~R128_UPLOAD_SETUP;
  247         }
  248 
  249         if (dirty & R128_UPLOAD_MASKS) {
  250                 r128_emit_masks(dev_priv);
  251                 sarea_priv->dirty &= ~R128_UPLOAD_MASKS;
  252         }
  253 
  254         if (dirty & R128_UPLOAD_WINDOW) {
  255                 r128_emit_window(dev_priv);
  256                 sarea_priv->dirty &= ~R128_UPLOAD_WINDOW;
  257         }
  258 
  259         if (dirty & R128_UPLOAD_TEX0) {
  260                 r128_emit_tex0(dev_priv);
  261                 sarea_priv->dirty &= ~R128_UPLOAD_TEX0;
  262         }
  263 
  264         if (dirty & R128_UPLOAD_TEX1) {
  265                 r128_emit_tex1(dev_priv);
  266                 sarea_priv->dirty &= ~R128_UPLOAD_TEX1;
  267         }
  268 
  269         /* Turn off the texture cache flushing */
  270         sarea_priv->context_state.tex_cntl_c &= ~R128_TEX_CACHE_FLUSH;
  271 
  272         sarea_priv->dirty &= ~R128_REQUIRE_QUIESCENCE;
  273 }
  274 
  275 #if R128_PERFORMANCE_BOXES
  276 /* ================================================================
  277  * Performance monitoring functions
  278  */
  279 
  280 static void r128_clear_box(drm_r128_private_t * dev_priv,
  281                            int x, int y, int w, int h, int r, int g, int b)
  282 {
  283         u32 pitch, offset;
  284         u32 fb_bpp, color;
  285         RING_LOCALS;
  286 
  287         switch (dev_priv->fb_bpp) {
  288         case 16:
  289                 fb_bpp = R128_GMC_DST_16BPP;
  290                 color = (((r & 0xf8) << 8) |
  291                          ((g & 0xfc) << 3) | ((b & 0xf8) >> 3));
  292                 break;
  293         case 24:
  294                 fb_bpp = R128_GMC_DST_24BPP;
  295                 color = ((r << 16) | (g << 8) | b);
  296                 break;
  297         case 32:
  298                 fb_bpp = R128_GMC_DST_32BPP;
  299                 color = (((0xff) << 24) | (r << 16) | (g << 8) | b);
  300                 break;
  301         default:
  302                 return;
  303         }
  304 
  305         offset = dev_priv->back_offset;
  306         pitch = dev_priv->back_pitch >> 3;
  307 
  308         BEGIN_RING(6);
  309 
  310         OUT_RING(CCE_PACKET3(R128_CNTL_PAINT_MULTI, 4));
  311         OUT_RING(R128_GMC_DST_PITCH_OFFSET_CNTL |
  312                  R128_GMC_BRUSH_SOLID_COLOR |
  313                  fb_bpp |
  314                  R128_GMC_SRC_DATATYPE_COLOR |
  315                  R128_ROP3_P |
  316                  R128_GMC_CLR_CMP_CNTL_DIS | R128_GMC_AUX_CLIP_DIS);
  317 
  318         OUT_RING((pitch << 21) | (offset >> 5));
  319         OUT_RING(color);
  320 
  321         OUT_RING((x << 16) | y);
  322         OUT_RING((w << 16) | h);
  323 
  324         ADVANCE_RING();
  325 }
  326 
  327 static void r128_cce_performance_boxes(drm_r128_private_t * dev_priv)
  328 {
  329         if (atomic_read(&dev_priv->idle_count) == 0) {
  330                 r128_clear_box(dev_priv, 64, 4, 8, 8, 0, 255, 0);
  331         } else {
  332                 atomic_set(&dev_priv->idle_count, 0);
  333         }
  334 }
  335 
  336 #endif
  337 
  338 /* ================================================================
  339  * CCE command dispatch functions
  340  */
  341 
  342 static void r128_print_dirty(const char *msg, unsigned int flags)
  343 {
  344         DRM_INFO("%s: (0x%x) %s%s%s%s%s%s%s%s%s\n",
  345                  msg,
  346                  flags,
  347                  (flags & R128_UPLOAD_CORE) ? "core, " : "",
  348                  (flags & R128_UPLOAD_CONTEXT) ? "context, " : "",
  349                  (flags & R128_UPLOAD_SETUP) ? "setup, " : "",
  350                  (flags & R128_UPLOAD_TEX0) ? "tex0, " : "",
  351                  (flags & R128_UPLOAD_TEX1) ? "tex1, " : "",
  352                  (flags & R128_UPLOAD_MASKS) ? "masks, " : "",
  353                  (flags & R128_UPLOAD_WINDOW) ? "window, " : "",
  354                  (flags & R128_UPLOAD_CLIPRECTS) ? "cliprects, " : "",
  355                  (flags & R128_REQUIRE_QUIESCENCE) ? "quiescence, " : "");
  356 }
  357 
  358 static void r128_cce_dispatch_clear(struct drm_device * dev,
  359                                     drm_r128_clear_t * clear)
  360 {
  361         drm_r128_private_t *dev_priv = dev->dev_private;
  362         drm_r128_sarea_t *sarea_priv = dev_priv->sarea_priv;
  363         int nbox = sarea_priv->nbox;
  364         struct drm_clip_rect *pbox = sarea_priv->boxes;
  365         unsigned int flags = clear->flags;
  366         int i;
  367         RING_LOCALS;
  368         DRM_DEBUG("\n");
  369 
  370         if (dev_priv->page_flipping && dev_priv->current_page == 1) {
  371                 unsigned int tmp = flags;
  372 
  373                 flags &= ~(R128_FRONT | R128_BACK);
  374                 if (tmp & R128_FRONT)
  375                         flags |= R128_BACK;
  376                 if (tmp & R128_BACK)
  377                         flags |= R128_FRONT;
  378         }
  379 
  380         for (i = 0; i < nbox; i++) {
  381                 int x = pbox[i].x1;
  382                 int y = pbox[i].y1;
  383                 int w = pbox[i].x2 - x;
  384                 int h = pbox[i].y2 - y;
  385 
  386                 DRM_DEBUG("dispatch clear %d,%d-%d,%d flags 0x%x\n",
  387                           pbox[i].x1, pbox[i].y1, pbox[i].x2,
  388                           pbox[i].y2, flags);
  389 
  390                 if (flags & (R128_FRONT | R128_BACK)) {
  391                         BEGIN_RING(2);
  392 
  393                         OUT_RING(CCE_PACKET0(R128_DP_WRITE_MASK, 0));
  394                         OUT_RING(clear->color_mask);
  395 
  396                         ADVANCE_RING();
  397                 }
  398 
  399                 if (flags & R128_FRONT) {
  400                         BEGIN_RING(6);
  401 
  402                         OUT_RING(CCE_PACKET3(R128_CNTL_PAINT_MULTI, 4));
  403                         OUT_RING(R128_GMC_DST_PITCH_OFFSET_CNTL |
  404                                  R128_GMC_BRUSH_SOLID_COLOR |
  405                                  (dev_priv->color_fmt << 8) |
  406                                  R128_GMC_SRC_DATATYPE_COLOR |
  407                                  R128_ROP3_P |
  408                                  R128_GMC_CLR_CMP_CNTL_DIS |
  409                                  R128_GMC_AUX_CLIP_DIS);
  410 
  411                         OUT_RING(dev_priv->front_pitch_offset_c);
  412                         OUT_RING(clear->clear_color);
  413 
  414                         OUT_RING((x << 16) | y);
  415                         OUT_RING((w << 16) | h);
  416 
  417                         ADVANCE_RING();
  418                 }
  419 
  420                 if (flags & R128_BACK) {
  421                         BEGIN_RING(6);
  422 
  423                         OUT_RING(CCE_PACKET3(R128_CNTL_PAINT_MULTI, 4));
  424                         OUT_RING(R128_GMC_DST_PITCH_OFFSET_CNTL |
  425                                  R128_GMC_BRUSH_SOLID_COLOR |
  426                                  (dev_priv->color_fmt << 8) |
  427                                  R128_GMC_SRC_DATATYPE_COLOR |
  428                                  R128_ROP3_P |
  429                                  R128_GMC_CLR_CMP_CNTL_DIS |
  430                                  R128_GMC_AUX_CLIP_DIS);
  431 
  432                         OUT_RING(dev_priv->back_pitch_offset_c);
  433                         OUT_RING(clear->clear_color);
  434 
  435                         OUT_RING((x << 16) | y);
  436                         OUT_RING((w << 16) | h);
  437 
  438                         ADVANCE_RING();
  439                 }
  440 
  441                 if (flags & R128_DEPTH) {
  442                         BEGIN_RING(6);
  443 
  444                         OUT_RING(CCE_PACKET3(R128_CNTL_PAINT_MULTI, 4));
  445                         OUT_RING(R128_GMC_DST_PITCH_OFFSET_CNTL |
  446                                  R128_GMC_BRUSH_SOLID_COLOR |
  447                                  (dev_priv->depth_fmt << 8) |
  448                                  R128_GMC_SRC_DATATYPE_COLOR |
  449                                  R128_ROP3_P |
  450                                  R128_GMC_CLR_CMP_CNTL_DIS |
  451                                  R128_GMC_AUX_CLIP_DIS | R128_GMC_WR_MSK_DIS);
  452 
  453                         OUT_RING(dev_priv->depth_pitch_offset_c);
  454                         OUT_RING(clear->clear_depth);
  455 
  456                         OUT_RING((x << 16) | y);
  457                         OUT_RING((w << 16) | h);
  458 
  459                         ADVANCE_RING();
  460                 }
  461         }
  462 }
  463 
  464 static void r128_cce_dispatch_swap(struct drm_device * dev)
  465 {
  466         drm_r128_private_t *dev_priv = dev->dev_private;
  467         drm_r128_sarea_t *sarea_priv = dev_priv->sarea_priv;
  468         int nbox = sarea_priv->nbox;
  469         struct drm_clip_rect *pbox = sarea_priv->boxes;
  470         int i;
  471         RING_LOCALS;
  472         DRM_DEBUG("\n");
  473 
  474 #if R128_PERFORMANCE_BOXES
  475         /* Do some trivial performance monitoring...
  476          */
  477         r128_cce_performance_boxes(dev_priv);
  478 #endif
  479 
  480         for (i = 0; i < nbox; i++) {
  481                 int x = pbox[i].x1;
  482                 int y = pbox[i].y1;
  483                 int w = pbox[i].x2 - x;
  484                 int h = pbox[i].y2 - y;
  485 
  486                 BEGIN_RING(7);
  487 
  488                 OUT_RING(CCE_PACKET3(R128_CNTL_BITBLT_MULTI, 5));
  489                 OUT_RING(R128_GMC_SRC_PITCH_OFFSET_CNTL |
  490                          R128_GMC_DST_PITCH_OFFSET_CNTL |
  491                          R128_GMC_BRUSH_NONE |
  492                          (dev_priv->color_fmt << 8) |
  493                          R128_GMC_SRC_DATATYPE_COLOR |
  494                          R128_ROP3_S |
  495                          R128_DP_SRC_SOURCE_MEMORY |
  496                          R128_GMC_CLR_CMP_CNTL_DIS |
  497                          R128_GMC_AUX_CLIP_DIS | R128_GMC_WR_MSK_DIS);
  498 
  499                 /* Make this work even if front & back are flipped:
  500                  */
  501                 if (dev_priv->current_page == 0) {
  502                         OUT_RING(dev_priv->back_pitch_offset_c);
  503                         OUT_RING(dev_priv->front_pitch_offset_c);
  504                 } else {
  505                         OUT_RING(dev_priv->front_pitch_offset_c);
  506                         OUT_RING(dev_priv->back_pitch_offset_c);
  507                 }
  508 
  509                 OUT_RING((x << 16) | y);
  510                 OUT_RING((x << 16) | y);
  511                 OUT_RING((w << 16) | h);
  512 
  513                 ADVANCE_RING();
  514         }
  515 
  516         /* Increment the frame counter.  The client-side 3D driver must
  517          * throttle the framerate by waiting for this value before
  518          * performing the swapbuffer ioctl.
  519          */
  520         dev_priv->sarea_priv->last_frame++;
  521 
  522         BEGIN_RING(2);
  523 
  524         OUT_RING(CCE_PACKET0(R128_LAST_FRAME_REG, 0));
  525         OUT_RING(dev_priv->sarea_priv->last_frame);
  526 
  527         ADVANCE_RING();
  528 }
  529 
  530 static void r128_cce_dispatch_flip(struct drm_device * dev)
  531 {
  532         drm_r128_private_t *dev_priv = dev->dev_private;
  533         RING_LOCALS;
  534         DRM_DEBUG("page=%d pfCurrentPage=%d\n",
  535                   dev_priv->current_page, dev_priv->sarea_priv->pfCurrentPage);
  536 
  537 #if R128_PERFORMANCE_BOXES
  538         /* Do some trivial performance monitoring...
  539          */
  540         r128_cce_performance_boxes(dev_priv);
  541 #endif
  542 
  543         BEGIN_RING(4);
  544 
  545         R128_WAIT_UNTIL_PAGE_FLIPPED();
  546         OUT_RING(CCE_PACKET0(R128_CRTC_OFFSET, 0));
  547 
  548         if (dev_priv->current_page == 0) {
  549                 OUT_RING(dev_priv->back_offset);
  550         } else {
  551                 OUT_RING(dev_priv->front_offset);
  552         }
  553 
  554         ADVANCE_RING();
  555 
  556         /* Increment the frame counter.  The client-side 3D driver must
  557          * throttle the framerate by waiting for this value before
  558          * performing the swapbuffer ioctl.
  559          */
  560         dev_priv->sarea_priv->last_frame++;
  561         dev_priv->sarea_priv->pfCurrentPage = dev_priv->current_page =
  562             1 - dev_priv->current_page;
  563 
  564         BEGIN_RING(2);
  565 
  566         OUT_RING(CCE_PACKET0(R128_LAST_FRAME_REG, 0));
  567         OUT_RING(dev_priv->sarea_priv->last_frame);
  568 
  569         ADVANCE_RING();
  570 }
  571 
  572 static void r128_cce_dispatch_vertex(struct drm_device * dev, struct drm_buf * buf)
  573 {
  574         drm_r128_private_t *dev_priv = dev->dev_private;
  575         drm_r128_buf_priv_t *buf_priv = buf->dev_private;
  576         drm_r128_sarea_t *sarea_priv = dev_priv->sarea_priv;
  577         int format = sarea_priv->vc_format;
  578         int offset = buf->bus_address;
  579         int size = buf->used;
  580         int prim = buf_priv->prim;
  581         int i = 0;
  582         RING_LOCALS;
  583         DRM_DEBUG("buf=%d nbox=%d\n", buf->idx, sarea_priv->nbox);
  584 
  585         if (0)
  586                 r128_print_dirty("dispatch_vertex", sarea_priv->dirty);
  587 
  588         if (buf->used) {
  589                 buf_priv->dispatched = 1;
  590 
  591                 if (sarea_priv->dirty & ~R128_UPLOAD_CLIPRECTS) {
  592                         r128_emit_state(dev_priv);
  593                 }
  594 
  595                 do {
  596                         /* Emit the next set of up to three cliprects */
  597                         if (i < sarea_priv->nbox) {
  598                                 r128_emit_clip_rects(dev_priv,
  599                                                      &sarea_priv->boxes[i],
  600                                                      sarea_priv->nbox - i);
  601                         }
  602 
  603                         /* Emit the vertex buffer rendering commands */
  604                         BEGIN_RING(5);
  605 
  606                         OUT_RING(CCE_PACKET3(R128_3D_RNDR_GEN_INDX_PRIM, 3));
  607                         OUT_RING(offset);
  608                         OUT_RING(size);
  609                         OUT_RING(format);
  610                         OUT_RING(prim | R128_CCE_VC_CNTL_PRIM_WALK_LIST |
  611                                  (size << R128_CCE_VC_CNTL_NUM_SHIFT));
  612 
  613                         ADVANCE_RING();
  614 
  615                         i += 3;
  616                 } while (i < sarea_priv->nbox);
  617         }
  618 
  619         if (buf_priv->discard) {
  620                 buf_priv->age = dev_priv->sarea_priv->last_dispatch;
  621 
  622                 /* Emit the vertex buffer age */
  623                 BEGIN_RING(2);
  624 
  625                 OUT_RING(CCE_PACKET0(R128_LAST_DISPATCH_REG, 0));
  626                 OUT_RING(buf_priv->age);
  627 
  628                 ADVANCE_RING();
  629 
  630                 buf->pending = 1;
  631                 buf->used = 0;
  632                 /* FIXME: Check dispatched field */
  633                 buf_priv->dispatched = 0;
  634         }
  635 
  636         dev_priv->sarea_priv->last_dispatch++;
  637 
  638         sarea_priv->dirty &= ~R128_UPLOAD_CLIPRECTS;
  639         sarea_priv->nbox = 0;
  640 }
  641 
  642 static void r128_cce_dispatch_indirect(struct drm_device * dev,
  643                                        struct drm_buf * buf, int start, int end)
  644 {
  645         drm_r128_private_t *dev_priv = dev->dev_private;
  646         drm_r128_buf_priv_t *buf_priv = buf->dev_private;
  647         RING_LOCALS;
  648         DRM_DEBUG("indirect: buf=%d s=0x%x e=0x%x\n", buf->idx, start, end);
  649 
  650         if (start != end) {
  651                 int offset = buf->bus_address + start;
  652                 int dwords = (end - start + 3) / sizeof(u32);
  653 
  654                 /* Indirect buffer data must be an even number of
  655                  * dwords, so if we've been given an odd number we must
  656                  * pad the data with a Type-2 CCE packet.
  657                  */
  658                 if (dwords & 1) {
  659                         u32 *data = (u32 *)
  660                             ((char *)dev->agp_buffer_map->virtual
  661                              + buf->offset + start);
  662                         data[dwords++] = cpu_to_le32(R128_CCE_PACKET2);
  663                 }
  664 
  665                 buf_priv->dispatched = 1;
  666 
  667                 /* Fire off the indirect buffer */
  668                 BEGIN_RING(3);
  669 
  670                 OUT_RING(CCE_PACKET0(R128_PM4_IW_INDOFF, 1));
  671                 OUT_RING(offset);
  672                 OUT_RING(dwords);
  673 
  674                 ADVANCE_RING();
  675         }
  676 
  677         if (buf_priv->discard) {
  678                 buf_priv->age = dev_priv->sarea_priv->last_dispatch;
  679 
  680                 /* Emit the indirect buffer age */
  681                 BEGIN_RING(2);
  682 
  683                 OUT_RING(CCE_PACKET0(R128_LAST_DISPATCH_REG, 0));
  684                 OUT_RING(buf_priv->age);
  685 
  686                 ADVANCE_RING();
  687 
  688                 buf->pending = 1;
  689                 buf->used = 0;
  690                 /* FIXME: Check dispatched field */
  691                 buf_priv->dispatched = 0;
  692         }
  693 
  694         dev_priv->sarea_priv->last_dispatch++;
  695 }
  696 
  697 static void r128_cce_dispatch_indices(struct drm_device * dev,
  698                                       struct drm_buf * buf,
  699                                       int start, int end, int count)
  700 {
  701         drm_r128_private_t *dev_priv = dev->dev_private;
  702         drm_r128_buf_priv_t *buf_priv = buf->dev_private;
  703         drm_r128_sarea_t *sarea_priv = dev_priv->sarea_priv;
  704         int format = sarea_priv->vc_format;
  705         int offset = dev->agp_buffer_map->offset - dev_priv->cce_buffers_offset;
  706         int prim = buf_priv->prim;
  707         u32 *data;
  708         int dwords;
  709         int i = 0;
  710         RING_LOCALS;
  711         DRM_DEBUG("indices: s=%d e=%d c=%d\n", start, end, count);
  712 
  713         if (0)
  714                 r128_print_dirty("dispatch_indices", sarea_priv->dirty);
  715 
  716         if (start != end) {
  717                 buf_priv->dispatched = 1;
  718 
  719                 if (sarea_priv->dirty & ~R128_UPLOAD_CLIPRECTS) {
  720                         r128_emit_state(dev_priv);
  721                 }
  722 
  723                 dwords = (end - start + 3) / sizeof(u32);
  724 
  725                 data = (u32 *) ((char *)dev->agp_buffer_map->virtual
  726                                 + buf->offset + start);
  727 
  728                 data[0] = cpu_to_le32(CCE_PACKET3(R128_3D_RNDR_GEN_INDX_PRIM,
  729                                                   dwords - 2));
  730 
  731                 data[1] = cpu_to_le32(offset);
  732                 data[2] = cpu_to_le32(R128_MAX_VB_VERTS);
  733                 data[3] = cpu_to_le32(format);
  734                 data[4] = cpu_to_le32((prim | R128_CCE_VC_CNTL_PRIM_WALK_IND |
  735                                        (count << 16)));
  736 
  737                 if (count & 0x1) {
  738 #ifdef __LITTLE_ENDIAN
  739                         data[dwords - 1] &= 0x0000ffff;
  740 #else
  741                         data[dwords - 1] &= 0xffff0000;
  742 #endif
  743                 }
  744 
  745                 do {
  746                         /* Emit the next set of up to three cliprects */
  747                         if (i < sarea_priv->nbox) {
  748                                 r128_emit_clip_rects(dev_priv,
  749                                                      &sarea_priv->boxes[i],
  750                                                      sarea_priv->nbox - i);
  751                         }
  752 
  753                         r128_cce_dispatch_indirect(dev, buf, start, end);
  754 
  755                         i += 3;
  756                 } while (i < sarea_priv->nbox);
  757         }
  758 
  759         if (buf_priv->discard) {
  760                 buf_priv->age = dev_priv->sarea_priv->last_dispatch;
  761 
  762                 /* Emit the vertex buffer age */
  763                 BEGIN_RING(2);
  764 
  765                 OUT_RING(CCE_PACKET0(R128_LAST_DISPATCH_REG, 0));
  766                 OUT_RING(buf_priv->age);
  767 
  768                 ADVANCE_RING();
  769 
  770                 buf->pending = 1;
  771                 /* FIXME: Check dispatched field */
  772                 buf_priv->dispatched = 0;
  773         }
  774 
  775         dev_priv->sarea_priv->last_dispatch++;
  776 
  777         sarea_priv->dirty &= ~R128_UPLOAD_CLIPRECTS;
  778         sarea_priv->nbox = 0;
  779 }
  780 
  781 static int r128_cce_dispatch_blit(struct drm_device * dev,
  782                                   struct drm_file *file_priv,
  783                                   drm_r128_blit_t * blit)
  784 {
  785         drm_r128_private_t *dev_priv = dev->dev_private;
  786         struct drm_device_dma *dma = dev->dma;
  787         struct drm_buf *buf;
  788         drm_r128_buf_priv_t *buf_priv;
  789         u32 *data;
  790         int dword_shift, dwords;
  791         RING_LOCALS;
  792         DRM_DEBUG("\n");
  793 
  794         /* The compiler won't optimize away a division by a variable,
  795          * even if the only legal values are powers of two.  Thus, we'll
  796          * use a shift instead.
  797          */
  798         switch (blit->format) {
  799         case R128_DATATYPE_ARGB8888:
  800                 dword_shift = 0;
  801                 break;
  802         case R128_DATATYPE_ARGB1555:
  803         case R128_DATATYPE_RGB565:
  804         case R128_DATATYPE_ARGB4444:
  805         case R128_DATATYPE_YVYU422:
  806         case R128_DATATYPE_VYUY422:
  807                 dword_shift = 1;
  808                 break;
  809         case R128_DATATYPE_CI8:
  810         case R128_DATATYPE_RGB8:
  811                 dword_shift = 2;
  812                 break;
  813         default:
  814                 DRM_ERROR("invalid blit format %d\n", blit->format);
  815                 return -EINVAL;
  816         }
  817 
  818         /* Flush the pixel cache, and mark the contents as Read Invalid.
  819          * This ensures no pixel data gets mixed up with the texture
  820          * data from the host data blit, otherwise part of the texture
  821          * image may be corrupted.
  822          */
  823         BEGIN_RING(2);
  824 
  825         OUT_RING(CCE_PACKET0(R128_PC_GUI_CTLSTAT, 0));
  826         OUT_RING(R128_PC_RI_GUI | R128_PC_FLUSH_GUI);
  827 
  828         ADVANCE_RING();
  829 
  830         /* Dispatch the indirect buffer.
  831          */
  832         buf = dma->buflist[blit->idx];
  833         buf_priv = buf->dev_private;
  834 
  835         if (buf->file_priv != file_priv) {
  836                 DRM_ERROR("process %d using buffer owned by %p\n",
  837                           DRM_CURRENTPID, buf->file_priv);
  838                 return -EINVAL;
  839         }
  840         if (buf->pending) {
  841                 DRM_ERROR("sending pending buffer %d\n", blit->idx);
  842                 return -EINVAL;
  843         }
  844 
  845         buf_priv->discard = 1;
  846 
  847         dwords = (blit->width * blit->height) >> dword_shift;
  848 
  849         data = (u32 *) ((char *)dev->agp_buffer_map->handle + buf->offset);
  850 
  851         data[0] = cpu_to_le32(CCE_PACKET3(R128_CNTL_HOSTDATA_BLT, dwords + 6));
  852         data[1] = cpu_to_le32((R128_GMC_DST_PITCH_OFFSET_CNTL |
  853                                R128_GMC_BRUSH_NONE |
  854                                (blit->format << 8) |
  855                                R128_GMC_SRC_DATATYPE_COLOR |
  856                                R128_ROP3_S |
  857                                R128_DP_SRC_SOURCE_HOST_DATA |
  858                                R128_GMC_CLR_CMP_CNTL_DIS |
  859                                R128_GMC_AUX_CLIP_DIS | R128_GMC_WR_MSK_DIS));
  860 
  861         data[2] = cpu_to_le32((blit->pitch << 21) | (blit->offset >> 5));
  862         data[3] = cpu_to_le32(0xffffffff);
  863         data[4] = cpu_to_le32(0xffffffff);
  864         data[5] = cpu_to_le32((blit->y << 16) | blit->x);
  865         data[6] = cpu_to_le32((blit->height << 16) | blit->width);
  866         data[7] = cpu_to_le32(dwords);
  867 
  868         buf->used = (dwords + 8) * sizeof(u32);
  869 
  870         r128_cce_dispatch_indirect(dev, buf, 0, buf->used);
  871 
  872         /* Flush the pixel cache after the blit completes.  This ensures
  873          * the texture data is written out to memory before rendering
  874          * continues.
  875          */
  876         BEGIN_RING(2);
  877 
  878         OUT_RING(CCE_PACKET0(R128_PC_GUI_CTLSTAT, 0));
  879         OUT_RING(R128_PC_FLUSH_GUI);
  880 
  881         ADVANCE_RING();
  882 
  883         return 0;
  884 }
  885 
  886 /* ================================================================
  887  * Tiled depth buffer management
  888  *
  889  * FIXME: These should all set the destination write mask for when we
  890  * have hardware stencil support.
  891  */
  892 
  893 static int r128_cce_dispatch_write_span(struct drm_device * dev,
  894                                         drm_r128_depth_t * depth)
  895 {
  896         drm_r128_private_t *dev_priv = dev->dev_private;
  897         int count, x, y;
  898         u32 *buffer;
  899         u8 *mask;
  900         int i, buffer_size, mask_size;
  901         RING_LOCALS;
  902         DRM_DEBUG("\n");
  903 
  904         count = depth->n;
  905         if (count > 4096 || count <= 0)
  906                 return -EMSGSIZE;
  907 
  908         if (DRM_COPY_FROM_USER(&x, depth->x, sizeof(x))) {
  909                 return -EFAULT;
  910         }
  911         if (DRM_COPY_FROM_USER(&y, depth->y, sizeof(y))) {
  912                 return -EFAULT;
  913         }
  914 
  915         buffer_size = depth->n * sizeof(u32);
  916         buffer = drm_alloc(buffer_size, DRM_MEM_BUFS);
  917         if (buffer == NULL)
  918                 return -ENOMEM;
  919         if (DRM_COPY_FROM_USER(buffer, depth->buffer, buffer_size)) {
  920                 drm_free(buffer, buffer_size, DRM_MEM_BUFS);
  921                 return -EFAULT;
  922         }
  923 
  924         mask_size = depth->n * sizeof(u8);
  925         if (depth->mask) {
  926                 mask = drm_alloc(mask_size, DRM_MEM_BUFS);
  927                 if (mask == NULL) {
  928                         drm_free(buffer, buffer_size, DRM_MEM_BUFS);
  929                         return -ENOMEM;
  930                 }
  931                 if (DRM_COPY_FROM_USER(mask, depth->mask, mask_size)) {
  932                         drm_free(buffer, buffer_size, DRM_MEM_BUFS);
  933                         drm_free(mask, mask_size, DRM_MEM_BUFS);
  934                         return -EFAULT;
  935                 }
  936 
  937                 for (i = 0; i < count; i++, x++) {
  938                         if (mask[i]) {
  939                                 BEGIN_RING(6);
  940 
  941                                 OUT_RING(CCE_PACKET3(R128_CNTL_PAINT_MULTI, 4));
  942                                 OUT_RING(R128_GMC_DST_PITCH_OFFSET_CNTL |
  943                                          R128_GMC_BRUSH_SOLID_COLOR |
  944                                          (dev_priv->depth_fmt << 8) |
  945                                          R128_GMC_SRC_DATATYPE_COLOR |
  946                                          R128_ROP3_P |
  947                                          R128_GMC_CLR_CMP_CNTL_DIS |
  948                                          R128_GMC_WR_MSK_DIS);
  949 
  950                                 OUT_RING(dev_priv->depth_pitch_offset_c);
  951                                 OUT_RING(buffer[i]);
  952 
  953                                 OUT_RING((x << 16) | y);
  954                                 OUT_RING((1 << 16) | 1);
  955 
  956                                 ADVANCE_RING();
  957                         }
  958                 }
  959 
  960                 drm_free(mask, mask_size, DRM_MEM_BUFS);
  961         } else {
  962                 for (i = 0; i < count; i++, x++) {
  963                         BEGIN_RING(6);
  964 
  965                         OUT_RING(CCE_PACKET3(R128_CNTL_PAINT_MULTI, 4));
  966                         OUT_RING(R128_GMC_DST_PITCH_OFFSET_CNTL |
  967                                  R128_GMC_BRUSH_SOLID_COLOR |
  968                                  (dev_priv->depth_fmt << 8) |
  969                                  R128_GMC_SRC_DATATYPE_COLOR |
  970                                  R128_ROP3_P |
  971                                  R128_GMC_CLR_CMP_CNTL_DIS |
  972                                  R128_GMC_WR_MSK_DIS);
  973 
  974                         OUT_RING(dev_priv->depth_pitch_offset_c);
  975                         OUT_RING(buffer[i]);
  976 
  977                         OUT_RING((x << 16) | y);
  978                         OUT_RING((1 << 16) | 1);
  979 
  980                         ADVANCE_RING();
  981                 }
  982         }
  983 
  984         drm_free(buffer, buffer_size, DRM_MEM_BUFS);
  985 
  986         return 0;
  987 }
  988 
  989 static int r128_cce_dispatch_write_pixels(struct drm_device * dev,
  990                                           drm_r128_depth_t * depth)
  991 {
  992         drm_r128_private_t *dev_priv = dev->dev_private;
  993         int count, *x, *y;
  994         u32 *buffer;
  995         u8 *mask;
  996         int i, xbuf_size, ybuf_size, buffer_size, mask_size;
  997         RING_LOCALS;
  998         DRM_DEBUG("\n");
  999 
 1000         count = depth->n;
 1001         if (count > 4096 || count <= 0)
 1002                 return -EMSGSIZE;
 1003 
 1004         xbuf_size = count * sizeof(*x);
 1005         ybuf_size = count * sizeof(*y);
 1006         x = drm_alloc(xbuf_size, DRM_MEM_BUFS);
 1007         if (x == NULL) {
 1008                 return -ENOMEM;
 1009         }
 1010         y = drm_alloc(ybuf_size, DRM_MEM_BUFS);
 1011         if (y == NULL) {
 1012                 drm_free(x, xbuf_size, DRM_MEM_BUFS);
 1013                 return -ENOMEM;
 1014         }
 1015         if (DRM_COPY_FROM_USER(x, depth->x, xbuf_size)) {
 1016                 drm_free(x, xbuf_size, DRM_MEM_BUFS);
 1017                 drm_free(y, ybuf_size, DRM_MEM_BUFS);
 1018                 return -EFAULT;
 1019         }
 1020         if (DRM_COPY_FROM_USER(y, depth->y, xbuf_size)) {
 1021                 drm_free(x, xbuf_size, DRM_MEM_BUFS);
 1022                 drm_free(y, ybuf_size, DRM_MEM_BUFS);
 1023                 return -EFAULT;
 1024         }
 1025 
 1026         buffer_size = depth->n * sizeof(u32);
 1027         buffer = drm_alloc(buffer_size, DRM_MEM_BUFS);
 1028         if (buffer == NULL) {
 1029                 drm_free(x, xbuf_size, DRM_MEM_BUFS);
 1030                 drm_free(y, ybuf_size, DRM_MEM_BUFS);
 1031                 return -ENOMEM;
 1032         }
 1033         if (DRM_COPY_FROM_USER(buffer, depth->buffer, buffer_size)) {
 1034                 drm_free(x, xbuf_size, DRM_MEM_BUFS);
 1035                 drm_free(y, ybuf_size, DRM_MEM_BUFS);
 1036                 drm_free(buffer, buffer_size, DRM_MEM_BUFS);
 1037                 return -EFAULT;
 1038         }
 1039 
 1040         if (depth->mask) {
 1041                 mask_size = depth->n * sizeof(u8);
 1042                 mask = drm_alloc(mask_size, DRM_MEM_BUFS);
 1043                 if (mask == NULL) {
 1044                         drm_free(x, xbuf_size, DRM_MEM_BUFS);
 1045                         drm_free(y, ybuf_size, DRM_MEM_BUFS);
 1046                         drm_free(buffer, buffer_size, DRM_MEM_BUFS);
 1047                         return -ENOMEM;
 1048                 }
 1049                 if (DRM_COPY_FROM_USER(mask, depth->mask, mask_size)) {
 1050                         drm_free(x, xbuf_size, DRM_MEM_BUFS);
 1051                         drm_free(y, ybuf_size, DRM_MEM_BUFS);
 1052                         drm_free(buffer, buffer_size, DRM_MEM_BUFS);
 1053                         drm_free(mask, mask_size, DRM_MEM_BUFS);
 1054                         return -EFAULT;
 1055                 }
 1056 
 1057                 for (i = 0; i < count; i++) {
 1058                         if (mask[i]) {
 1059                                 BEGIN_RING(6);
 1060 
 1061                                 OUT_RING(CCE_PACKET3(R128_CNTL_PAINT_MULTI, 4));
 1062                                 OUT_RING(R128_GMC_DST_PITCH_OFFSET_CNTL |
 1063                                          R128_GMC_BRUSH_SOLID_COLOR |
 1064                                          (dev_priv->depth_fmt << 8) |
 1065                                          R128_GMC_SRC_DATATYPE_COLOR |
 1066                                          R128_ROP3_P |
 1067                                          R128_GMC_CLR_CMP_CNTL_DIS |
 1068                                          R128_GMC_WR_MSK_DIS);
 1069 
 1070                                 OUT_RING(dev_priv->depth_pitch_offset_c);
 1071                                 OUT_RING(buffer[i]);
 1072 
 1073                                 OUT_RING((x[i] << 16) | y[i]);
 1074                                 OUT_RING((1 << 16) | 1);
 1075 
 1076                                 ADVANCE_RING();
 1077                         }
 1078                 }
 1079 
 1080                 drm_free(mask, mask_size, DRM_MEM_BUFS);
 1081         } else {
 1082                 for (i = 0; i < count; i++) {
 1083                         BEGIN_RING(6);
 1084 
 1085                         OUT_RING(CCE_PACKET3(R128_CNTL_PAINT_MULTI, 4));
 1086                         OUT_RING(R128_GMC_DST_PITCH_OFFSET_CNTL |
 1087                                  R128_GMC_BRUSH_SOLID_COLOR |
 1088                                  (dev_priv->depth_fmt << 8) |
 1089                                  R128_GMC_SRC_DATATYPE_COLOR |
 1090                                  R128_ROP3_P |
 1091                                  R128_GMC_CLR_CMP_CNTL_DIS |
 1092                                  R128_GMC_WR_MSK_DIS);
 1093 
 1094                         OUT_RING(dev_priv->depth_pitch_offset_c);
 1095                         OUT_RING(buffer[i]);
 1096 
 1097                         OUT_RING((x[i] << 16) | y[i]);
 1098                         OUT_RING((1 << 16) | 1);
 1099 
 1100                         ADVANCE_RING();
 1101                 }
 1102         }
 1103 
 1104         drm_free(x, xbuf_size, DRM_MEM_BUFS);
 1105         drm_free(y, ybuf_size, DRM_MEM_BUFS);
 1106         drm_free(buffer, buffer_size, DRM_MEM_BUFS);
 1107 
 1108         return 0;
 1109 }
 1110 
 1111 static int r128_cce_dispatch_read_span(struct drm_device * dev,
 1112                                        drm_r128_depth_t * depth)
 1113 {
 1114         drm_r128_private_t *dev_priv = dev->dev_private;
 1115         int count, x, y;
 1116         RING_LOCALS;
 1117         DRM_DEBUG("\n");
 1118 
 1119         count = depth->n;
 1120         if (count > 4096 || count <= 0)
 1121                 return -EMSGSIZE;
 1122 
 1123         if (DRM_COPY_FROM_USER(&x, depth->x, sizeof(x))) {
 1124                 return -EFAULT;
 1125         }
 1126         if (DRM_COPY_FROM_USER(&y, depth->y, sizeof(y))) {
 1127                 return -EFAULT;
 1128         }
 1129 
 1130         BEGIN_RING(7);
 1131 
 1132         OUT_RING(CCE_PACKET3(R128_CNTL_BITBLT_MULTI, 5));
 1133         OUT_RING(R128_GMC_SRC_PITCH_OFFSET_CNTL |
 1134                  R128_GMC_DST_PITCH_OFFSET_CNTL |
 1135                  R128_GMC_BRUSH_NONE |
 1136                  (dev_priv->depth_fmt << 8) |
 1137                  R128_GMC_SRC_DATATYPE_COLOR |
 1138                  R128_ROP3_S |
 1139                  R128_DP_SRC_SOURCE_MEMORY |
 1140                  R128_GMC_CLR_CMP_CNTL_DIS | R128_GMC_WR_MSK_DIS);
 1141 
 1142         OUT_RING(dev_priv->depth_pitch_offset_c);
 1143         OUT_RING(dev_priv->span_pitch_offset_c);
 1144 
 1145         OUT_RING((x << 16) | y);
 1146         OUT_RING((0 << 16) | 0);
 1147         OUT_RING((count << 16) | 1);
 1148 
 1149         ADVANCE_RING();
 1150 
 1151         return 0;
 1152 }
 1153 
 1154 static int r128_cce_dispatch_read_pixels(struct drm_device * dev,
 1155                                          drm_r128_depth_t * depth)
 1156 {
 1157         drm_r128_private_t *dev_priv = dev->dev_private;
 1158         int count, *x, *y;
 1159         int i, xbuf_size, ybuf_size;
 1160         RING_LOCALS;
 1161         DRM_DEBUG("\n");
 1162 
 1163         count = depth->n;
 1164         if (count > 4096 || count <= 0)
 1165                 return -EMSGSIZE;
 1166 
 1167         if (count > dev_priv->depth_pitch) {
 1168                 count = dev_priv->depth_pitch;
 1169         }
 1170 
 1171         xbuf_size = count * sizeof(*x);
 1172         ybuf_size = count * sizeof(*y);
 1173         x = drm_alloc(xbuf_size, DRM_MEM_BUFS);
 1174         if (x == NULL) {
 1175                 return -ENOMEM;
 1176         }
 1177         y = drm_alloc(ybuf_size, DRM_MEM_BUFS);
 1178         if (y == NULL) {
 1179                 drm_free(x, xbuf_size, DRM_MEM_BUFS);
 1180                 return -ENOMEM;
 1181         }
 1182         if (DRM_COPY_FROM_USER(x, depth->x, xbuf_size)) {
 1183                 drm_free(x, xbuf_size, DRM_MEM_BUFS);
 1184                 drm_free(y, ybuf_size, DRM_MEM_BUFS);
 1185                 return -EFAULT;
 1186         }
 1187         if (DRM_COPY_FROM_USER(y, depth->y, ybuf_size)) {
 1188                 drm_free(x, xbuf_size, DRM_MEM_BUFS);
 1189                 drm_free(y, ybuf_size, DRM_MEM_BUFS);
 1190                 return -EFAULT;
 1191         }
 1192 
 1193         for (i = 0; i < count; i++) {
 1194                 BEGIN_RING(7);
 1195 
 1196                 OUT_RING(CCE_PACKET3(R128_CNTL_BITBLT_MULTI, 5));
 1197                 OUT_RING(R128_GMC_SRC_PITCH_OFFSET_CNTL |
 1198                          R128_GMC_DST_PITCH_OFFSET_CNTL |
 1199                          R128_GMC_BRUSH_NONE |
 1200                          (dev_priv->depth_fmt << 8) |
 1201                          R128_GMC_SRC_DATATYPE_COLOR |
 1202                          R128_ROP3_S |
 1203                          R128_DP_SRC_SOURCE_MEMORY |
 1204                          R128_GMC_CLR_CMP_CNTL_DIS | R128_GMC_WR_MSK_DIS);
 1205 
 1206                 OUT_RING(dev_priv->depth_pitch_offset_c);
 1207                 OUT_RING(dev_priv->span_pitch_offset_c);
 1208 
 1209                 OUT_RING((x[i] << 16) | y[i]);
 1210                 OUT_RING((i << 16) | 0);
 1211                 OUT_RING((1 << 16) | 1);
 1212 
 1213                 ADVANCE_RING();
 1214         }
 1215 
 1216         drm_free(x, xbuf_size, DRM_MEM_BUFS);
 1217         drm_free(y, ybuf_size, DRM_MEM_BUFS);
 1218 
 1219         return 0;
 1220 }
 1221 
 1222 /* ================================================================
 1223  * Polygon stipple
 1224  */
 1225 
 1226 static void r128_cce_dispatch_stipple(struct drm_device * dev, u32 * stipple)
 1227 {
 1228         drm_r128_private_t *dev_priv = dev->dev_private;
 1229         int i;
 1230         RING_LOCALS;
 1231         DRM_DEBUG("\n");
 1232 
 1233         BEGIN_RING(33);
 1234 
 1235         OUT_RING(CCE_PACKET0(R128_BRUSH_DATA0, 31));
 1236         for (i = 0; i < 32; i++) {
 1237                 OUT_RING(stipple[i]);
 1238         }
 1239 
 1240         ADVANCE_RING();
 1241 }
 1242 
 1243 /* ================================================================
 1244  * IOCTL functions
 1245  */
 1246 
 1247 static int r128_cce_clear(struct drm_device *dev, void *data, struct drm_file *file_priv)
 1248 {
 1249         drm_r128_private_t *dev_priv = dev->dev_private;
 1250         drm_r128_sarea_t *sarea_priv = dev_priv->sarea_priv;
 1251         drm_r128_clear_t *clear = data;
 1252         DRM_DEBUG("\n");
 1253 
 1254         LOCK_TEST_WITH_RETURN(dev, file_priv);
 1255 
 1256         RING_SPACE_TEST_WITH_RETURN(dev_priv);
 1257 
 1258         if (sarea_priv->nbox > R128_NR_SAREA_CLIPRECTS)
 1259                 sarea_priv->nbox = R128_NR_SAREA_CLIPRECTS;
 1260 
 1261         r128_cce_dispatch_clear(dev, clear);
 1262         COMMIT_RING();
 1263 
 1264         /* Make sure we restore the 3D state next time.
 1265          */
 1266         dev_priv->sarea_priv->dirty |= R128_UPLOAD_CONTEXT | R128_UPLOAD_MASKS;
 1267 
 1268         return 0;
 1269 }
 1270 
 1271 static int r128_do_init_pageflip(struct drm_device * dev)
 1272 {
 1273         drm_r128_private_t *dev_priv = dev->dev_private;
 1274         DRM_DEBUG("\n");
 1275 
 1276         dev_priv->crtc_offset = R128_READ(R128_CRTC_OFFSET);
 1277         dev_priv->crtc_offset_cntl = R128_READ(R128_CRTC_OFFSET_CNTL);
 1278 
 1279         R128_WRITE(R128_CRTC_OFFSET, dev_priv->front_offset);
 1280         R128_WRITE(R128_CRTC_OFFSET_CNTL,
 1281                    dev_priv->crtc_offset_cntl | R128_CRTC_OFFSET_FLIP_CNTL);
 1282 
 1283         dev_priv->page_flipping = 1;
 1284         dev_priv->current_page = 0;
 1285         dev_priv->sarea_priv->pfCurrentPage = dev_priv->current_page;
 1286 
 1287         return 0;
 1288 }
 1289 
 1290 static int r128_do_cleanup_pageflip(struct drm_device * dev)
 1291 {
 1292         drm_r128_private_t *dev_priv = dev->dev_private;
 1293         DRM_DEBUG("\n");
 1294 
 1295         R128_WRITE(R128_CRTC_OFFSET, dev_priv->crtc_offset);
 1296         R128_WRITE(R128_CRTC_OFFSET_CNTL, dev_priv->crtc_offset_cntl);
 1297 
 1298         if (dev_priv->current_page != 0) {
 1299                 r128_cce_dispatch_flip(dev);
 1300                 COMMIT_RING();
 1301         }
 1302 
 1303         dev_priv->page_flipping = 0;
 1304         return 0;
 1305 }
 1306 
 1307 /* Swapping and flipping are different operations, need different ioctls.
 1308  * They can & should be intermixed to support multiple 3d windows.
 1309  */
 1310 
 1311 static int r128_cce_flip(struct drm_device *dev, void *data, struct drm_file *file_priv)
 1312 {
 1313         drm_r128_private_t *dev_priv = dev->dev_private;
 1314         DRM_DEBUG("\n");
 1315 
 1316         LOCK_TEST_WITH_RETURN(dev, file_priv);
 1317 
 1318         RING_SPACE_TEST_WITH_RETURN(dev_priv);
 1319 
 1320         if (!dev_priv->page_flipping)
 1321                 r128_do_init_pageflip(dev);
 1322 
 1323         r128_cce_dispatch_flip(dev);
 1324 
 1325         COMMIT_RING();
 1326         return 0;
 1327 }
 1328 
 1329 static int r128_cce_swap(struct drm_device *dev, void *data, struct drm_file *file_priv)
 1330 {
 1331         drm_r128_private_t *dev_priv = dev->dev_private;
 1332         drm_r128_sarea_t *sarea_priv = dev_priv->sarea_priv;
 1333         DRM_DEBUG("\n");
 1334 
 1335         LOCK_TEST_WITH_RETURN(dev, file_priv);
 1336 
 1337         RING_SPACE_TEST_WITH_RETURN(dev_priv);
 1338 
 1339         if (sarea_priv->nbox > R128_NR_SAREA_CLIPRECTS)
 1340                 sarea_priv->nbox = R128_NR_SAREA_CLIPRECTS;
 1341 
 1342         r128_cce_dispatch_swap(dev);
 1343         dev_priv->sarea_priv->dirty |= (R128_UPLOAD_CONTEXT |
 1344                                         R128_UPLOAD_MASKS);
 1345 
 1346         COMMIT_RING();
 1347         return 0;
 1348 }
 1349 
 1350 static int r128_cce_vertex(struct drm_device *dev, void *data, struct drm_file *file_priv)
 1351 {
 1352         drm_r128_private_t *dev_priv = dev->dev_private;
 1353         struct drm_device_dma *dma = dev->dma;
 1354         struct drm_buf *buf;
 1355         drm_r128_buf_priv_t *buf_priv;
 1356         drm_r128_vertex_t *vertex = data;
 1357 
 1358         LOCK_TEST_WITH_RETURN(dev, file_priv);
 1359 
 1360         if (!dev_priv) {
 1361                 DRM_ERROR("called with no initialization\n");
 1362                 return -EINVAL;
 1363         }
 1364 
 1365         DRM_DEBUG("pid=%d index=%d count=%d discard=%d\n",
 1366                   DRM_CURRENTPID, vertex->idx, vertex->count, vertex->discard);
 1367 
 1368         if (vertex->idx < 0 || vertex->idx >= dma->buf_count) {
 1369                 DRM_ERROR("buffer index %d (of %d max)\n",
 1370                           vertex->idx, dma->buf_count - 1);
 1371                 return -EINVAL;
 1372         }
 1373         if (vertex->prim < 0 ||
 1374             vertex->prim > R128_CCE_VC_CNTL_PRIM_TYPE_TRI_TYPE2) {
 1375                 DRM_ERROR("buffer prim %d\n", vertex->prim);
 1376                 return -EINVAL;
 1377         }
 1378 
 1379         RING_SPACE_TEST_WITH_RETURN(dev_priv);
 1380         VB_AGE_TEST_WITH_RETURN(dev_priv);
 1381 
 1382         buf = dma->buflist[vertex->idx];
 1383         buf_priv = buf->dev_private;
 1384 
 1385         if (buf->file_priv != file_priv) {
 1386                 DRM_ERROR("process %d using buffer owned by %p\n",
 1387                           DRM_CURRENTPID, buf->file_priv);
 1388                 return -EINVAL;
 1389         }
 1390         if (buf->pending) {
 1391                 DRM_ERROR("sending pending buffer %d\n", vertex->idx);
 1392                 return -EINVAL;
 1393         }
 1394 
 1395         buf->used = vertex->count;
 1396         buf_priv->prim = vertex->prim;
 1397         buf_priv->discard = vertex->discard;
 1398 
 1399         r128_cce_dispatch_vertex(dev, buf);
 1400 
 1401         COMMIT_RING();
 1402         return 0;
 1403 }
 1404 
 1405 static int r128_cce_indices(struct drm_device *dev, void *data, struct drm_file *file_priv)
 1406 {
 1407         drm_r128_private_t *dev_priv = dev->dev_private;
 1408         struct drm_device_dma *dma = dev->dma;
 1409         struct drm_buf *buf;
 1410         drm_r128_buf_priv_t *buf_priv;
 1411         drm_r128_indices_t *elts = data;
 1412         int count;
 1413 
 1414         LOCK_TEST_WITH_RETURN(dev, file_priv);
 1415 
 1416         if (!dev_priv) {
 1417                 DRM_ERROR("called with no initialization\n");
 1418                 return -EINVAL;
 1419         }
 1420 
 1421         DRM_DEBUG("pid=%d buf=%d s=%d e=%d d=%d\n", DRM_CURRENTPID,
 1422                   elts->idx, elts->start, elts->end, elts->discard);
 1423 
 1424         if (elts->idx < 0 || elts->idx >= dma->buf_count) {
 1425                 DRM_ERROR("buffer index %d (of %d max)\n",
 1426                           elts->idx, dma->buf_count - 1);
 1427                 return -EINVAL;
 1428         }
 1429         if (elts->prim < 0 ||
 1430             elts->prim > R128_CCE_VC_CNTL_PRIM_TYPE_TRI_TYPE2) {
 1431                 DRM_ERROR("buffer prim %d\n", elts->prim);
 1432                 return -EINVAL;
 1433         }
 1434 
 1435         RING_SPACE_TEST_WITH_RETURN(dev_priv);
 1436         VB_AGE_TEST_WITH_RETURN(dev_priv);
 1437 
 1438         buf = dma->buflist[elts->idx];
 1439         buf_priv = buf->dev_private;
 1440 
 1441         if (buf->file_priv != file_priv) {
 1442                 DRM_ERROR("process %d using buffer owned by %p\n",
 1443                           DRM_CURRENTPID, buf->file_priv);
 1444                 return -EINVAL;
 1445         }
 1446         if (buf->pending) {
 1447                 DRM_ERROR("sending pending buffer %d\n", elts->idx);
 1448                 return -EINVAL;
 1449         }
 1450 
 1451         count = (elts->end - elts->start) / sizeof(u16);
 1452         elts->start -= R128_INDEX_PRIM_OFFSET;
 1453 
 1454         if (elts->start & 0x7) {
 1455                 DRM_ERROR("misaligned buffer 0x%x\n", elts->start);
 1456                 return -EINVAL;
 1457         }
 1458         if (elts->start < buf->used) {
 1459                 DRM_ERROR("no header 0x%x - 0x%x\n", elts->start, buf->used);
 1460                 return -EINVAL;
 1461         }
 1462 
 1463         buf->used = elts->end;
 1464         buf_priv->prim = elts->prim;
 1465         buf_priv->discard = elts->discard;
 1466 
 1467         r128_cce_dispatch_indices(dev, buf, elts->start, elts->end, count);
 1468 
 1469         COMMIT_RING();
 1470         return 0;
 1471 }
 1472 
 1473 static int r128_cce_blit(struct drm_device *dev, void *data, struct drm_file *file_priv)
 1474 {
 1475         struct drm_device_dma *dma = dev->dma;
 1476         drm_r128_private_t *dev_priv = dev->dev_private;
 1477         drm_r128_blit_t *blit = data;
 1478         int ret;
 1479 
 1480         LOCK_TEST_WITH_RETURN(dev, file_priv);
 1481 
 1482         DRM_DEBUG("pid=%d index=%d\n", DRM_CURRENTPID, blit->idx);
 1483 
 1484         if (blit->idx < 0 || blit->idx >= dma->buf_count) {
 1485                 DRM_ERROR("buffer index %d (of %d max)\n",
 1486                           blit->idx, dma->buf_count - 1);
 1487                 return -EINVAL;
 1488         }
 1489 
 1490         RING_SPACE_TEST_WITH_RETURN(dev_priv);
 1491         VB_AGE_TEST_WITH_RETURN(dev_priv);
 1492 
 1493         ret = r128_cce_dispatch_blit(dev, file_priv, blit);
 1494 
 1495         COMMIT_RING();
 1496         return ret;
 1497 }
 1498 
 1499 static int r128_cce_depth(struct drm_device *dev, void *data, struct drm_file *file_priv)
 1500 {
 1501         drm_r128_private_t *dev_priv = dev->dev_private;
 1502         drm_r128_depth_t *depth = data;
 1503         int ret;
 1504 
 1505         LOCK_TEST_WITH_RETURN(dev, file_priv);
 1506 
 1507         RING_SPACE_TEST_WITH_RETURN(dev_priv);
 1508 
 1509         ret = -EINVAL;
 1510         switch (depth->func) {
 1511         case R128_WRITE_SPAN:
 1512                 ret = r128_cce_dispatch_write_span(dev, depth);
 1513                 break;
 1514         case R128_WRITE_PIXELS:
 1515                 ret = r128_cce_dispatch_write_pixels(dev, depth);
 1516                 break;
 1517         case R128_READ_SPAN:
 1518                 ret = r128_cce_dispatch_read_span(dev, depth);
 1519                 break;
 1520         case R128_READ_PIXELS:
 1521                 ret = r128_cce_dispatch_read_pixels(dev, depth);
 1522                 break;
 1523         }
 1524 
 1525         COMMIT_RING();
 1526         return ret;
 1527 }
 1528 
 1529 static int r128_cce_stipple(struct drm_device *dev, void *data, struct drm_file *file_priv)
 1530 {
 1531         drm_r128_private_t *dev_priv = dev->dev_private;
 1532         drm_r128_stipple_t *stipple = data;
 1533         u32 mask[32];
 1534 
 1535         LOCK_TEST_WITH_RETURN(dev, file_priv);
 1536 
 1537         if (DRM_COPY_FROM_USER(&mask, stipple->mask, 32 * sizeof(u32)))
 1538                 return -EFAULT;
 1539 
 1540         RING_SPACE_TEST_WITH_RETURN(dev_priv);
 1541 
 1542         r128_cce_dispatch_stipple(dev, mask);
 1543 
 1544         COMMIT_RING();
 1545         return 0;
 1546 }
 1547 
 1548 static int r128_cce_indirect(struct drm_device *dev, void *data, struct drm_file *file_priv)
 1549 {
 1550         drm_r128_private_t *dev_priv = dev->dev_private;
 1551         struct drm_device_dma *dma = dev->dma;
 1552         struct drm_buf *buf;
 1553         drm_r128_buf_priv_t *buf_priv;
 1554         drm_r128_indirect_t *indirect = data;
 1555 #if 0
 1556         RING_LOCALS;
 1557 #endif
 1558 
 1559         LOCK_TEST_WITH_RETURN(dev, file_priv);
 1560 
 1561         if (!dev_priv) {
 1562                 DRM_ERROR("called with no initialization\n");
 1563                 return -EINVAL;
 1564         }
 1565 
 1566         DRM_DEBUG("idx=%d s=%d e=%d d=%d\n",
 1567                   indirect->idx, indirect->start, indirect->end,
 1568                   indirect->discard);
 1569 
 1570         if (indirect->idx < 0 || indirect->idx >= dma->buf_count) {
 1571                 DRM_ERROR("buffer index %d (of %d max)\n",
 1572                           indirect->idx, dma->buf_count - 1);
 1573                 return -EINVAL;
 1574         }
 1575 
 1576         buf = dma->buflist[indirect->idx];
 1577         buf_priv = buf->dev_private;
 1578 
 1579         if (buf->file_priv != file_priv) {
 1580                 DRM_ERROR("process %d using buffer owned by %p\n",
 1581                           DRM_CURRENTPID, buf->file_priv);
 1582                 return -EINVAL;
 1583         }
 1584         if (buf->pending) {
 1585                 DRM_ERROR("sending pending buffer %d\n", indirect->idx);
 1586                 return -EINVAL;
 1587         }
 1588 
 1589         if (indirect->start < buf->used) {
 1590                 DRM_ERROR("reusing indirect: start=0x%x actual=0x%x\n",
 1591                           indirect->start, buf->used);
 1592                 return -EINVAL;
 1593         }
 1594 
 1595         RING_SPACE_TEST_WITH_RETURN(dev_priv);
 1596         VB_AGE_TEST_WITH_RETURN(dev_priv);
 1597 
 1598         buf->used = indirect->end;
 1599         buf_priv->discard = indirect->discard;
 1600 
 1601 #if 0
 1602         /* Wait for the 3D stream to idle before the indirect buffer
 1603          * containing 2D acceleration commands is processed.
 1604          */
 1605         BEGIN_RING(2);
 1606         RADEON_WAIT_UNTIL_3D_IDLE();
 1607         ADVANCE_RING();
 1608 #endif
 1609 
 1610         /* Dispatch the indirect buffer full of commands from the
 1611          * X server.  This is insecure and is thus only available to
 1612          * privileged clients.
 1613          */
 1614         r128_cce_dispatch_indirect(dev, buf, indirect->start, indirect->end);
 1615 
 1616         COMMIT_RING();
 1617         return 0;
 1618 }
 1619 
 1620 static int r128_getparam(struct drm_device *dev, void *data, struct drm_file *file_priv)
 1621 {
 1622         drm_r128_private_t *dev_priv = dev->dev_private;
 1623         drm_r128_getparam_t *param = data;
 1624         int value;
 1625 
 1626         if (!dev_priv) {
 1627                 DRM_ERROR("called with no initialization\n");
 1628                 return -EINVAL;
 1629         }
 1630 
 1631         DRM_DEBUG("pid=%d\n", DRM_CURRENTPID);
 1632 
 1633         switch (param->param) {
 1634         case R128_PARAM_IRQ_NR:
 1635                 value = dev->irq;
 1636                 break;
 1637         default:
 1638                 return -EINVAL;
 1639         }
 1640 
 1641         if (DRM_COPY_TO_USER(param->value, &value, sizeof(int))) {
 1642                 DRM_ERROR("copy_to_user\n");
 1643                 return -EFAULT;
 1644         }
 1645 
 1646         return 0;
 1647 }
 1648 
 1649 void r128_driver_preclose(struct drm_device * dev, struct drm_file *file_priv)
 1650 {
 1651         if (dev->dev_private) {
 1652                 drm_r128_private_t *dev_priv = dev->dev_private;
 1653                 if (dev_priv->page_flipping) {
 1654                         r128_do_cleanup_pageflip(dev);
 1655                 }
 1656         }
 1657 }
 1658 
 1659 void r128_driver_lastclose(struct drm_device * dev)
 1660 {
 1661         r128_do_cleanup_cce(dev);
 1662 }
 1663 
 1664 struct drm_ioctl_desc r128_ioctls[] = {
 1665         DRM_IOCTL_DEF(DRM_R128_INIT, r128_cce_init, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
 1666         DRM_IOCTL_DEF(DRM_R128_CCE_START, r128_cce_start, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
 1667         DRM_IOCTL_DEF(DRM_R128_CCE_STOP, r128_cce_stop, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
 1668         DRM_IOCTL_DEF(DRM_R128_CCE_RESET, r128_cce_reset, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
 1669         DRM_IOCTL_DEF(DRM_R128_CCE_IDLE, r128_cce_idle, DRM_AUTH),
 1670         DRM_IOCTL_DEF(DRM_R128_RESET, r128_engine_reset, DRM_AUTH),
 1671         DRM_IOCTL_DEF(DRM_R128_FULLSCREEN, r128_fullscreen, DRM_AUTH),
 1672         DRM_IOCTL_DEF(DRM_R128_SWAP, r128_cce_swap, DRM_AUTH),
 1673         DRM_IOCTL_DEF(DRM_R128_FLIP, r128_cce_flip, DRM_AUTH),
 1674         DRM_IOCTL_DEF(DRM_R128_CLEAR, r128_cce_clear, DRM_AUTH),
 1675         DRM_IOCTL_DEF(DRM_R128_VERTEX, r128_cce_vertex, DRM_AUTH),
 1676         DRM_IOCTL_DEF(DRM_R128_INDICES, r128_cce_indices, DRM_AUTH),
 1677         DRM_IOCTL_DEF(DRM_R128_BLIT, r128_cce_blit, DRM_AUTH),
 1678         DRM_IOCTL_DEF(DRM_R128_DEPTH, r128_cce_depth, DRM_AUTH),
 1679         DRM_IOCTL_DEF(DRM_R128_STIPPLE, r128_cce_stipple, DRM_AUTH),
 1680         DRM_IOCTL_DEF(DRM_R128_INDIRECT, r128_cce_indirect, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
 1681         DRM_IOCTL_DEF(DRM_R128_GETPARAM, r128_getparam, DRM_AUTH),
 1682 };
 1683 
 1684 int r128_max_ioctl = DRM_ARRAY_SIZE(r128_ioctls);

Cache object: 0500614ff80d30abd1f0d097639e57dd


[ source navigation ] [ diff markup ] [ identifier search ] [ freetext search ] [ file search ] [ list types ] [ track identifier ]


This page is part of the FreeBSD/Linux Linux Kernel Cross-Reference, and was automatically generated using a modified version of the LXR engine.