]> git.kernelconcepts.de Git - karo-tx-linux.git/blob - drivers/gpu/drm/radeon/radeon_state.c
Merge remote branch 'korg/drm-radeon-testing' into drm-next-stage
[karo-tx-linux.git] / drivers / gpu / drm / radeon / radeon_state.c
1 /* radeon_state.c -- State support for Radeon -*- linux-c -*- */
2 /*
3  * Copyright 2000 VA Linux Systems, Inc., Fremont, California.
4  * All Rights Reserved.
5  *
6  * Permission is hereby granted, free of charge, to any person obtaining a
7  * copy of this software and associated documentation files (the "Software"),
8  * to deal in the Software without restriction, including without limitation
9  * the rights to use, copy, modify, merge, publish, distribute, sublicense,
10  * and/or sell copies of the Software, and to permit persons to whom the
11  * Software is furnished to do so, subject to the following conditions:
12  *
13  * The above copyright notice and this permission notice (including the next
14  * paragraph) shall be included in all copies or substantial portions of the
15  * Software.
16  *
17  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
18  * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
19  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
20  * PRECISION INSIGHT AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
21  * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
22  * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
23  * DEALINGS IN THE SOFTWARE.
24  *
25  * Authors:
26  *    Gareth Hughes <gareth@valinux.com>
27  *    Kevin E. Martin <martin@valinux.com>
28  */
29
30 #include "drmP.h"
31 #include "drm.h"
32 #include "drm_buffer.h"
33 #include "drm_sarea.h"
34 #include "radeon_drm.h"
35 #include "radeon_drv.h"
36
37 /* ================================================================
38  * Helper functions for client state checking and fixup
39  */
40
41 static __inline__ int radeon_check_and_fixup_offset(drm_radeon_private_t *
42                                                     dev_priv,
43                                                     struct drm_file * file_priv,
44                                                     u32 *offset)
45 {
46         u64 off = *offset;
47         u32 fb_end = dev_priv->fb_location + dev_priv->fb_size - 1;
48         struct drm_radeon_driver_file_fields *radeon_priv;
49
50         /* Hrm ... the story of the offset ... So this function converts
51          * the various ideas of what userland clients might have for an
52          * offset in the card address space into an offset into the card
53          * address space :) So with a sane client, it should just keep
54          * the value intact and just do some boundary checking. However,
55          * not all clients are sane. Some older clients pass us 0 based
56          * offsets relative to the start of the framebuffer and some may
57          * assume the AGP aperture it appended to the framebuffer, so we
58          * try to detect those cases and fix them up.
59          *
60          * Note: It might be a good idea here to make sure the offset lands
61          * in some "allowed" area to protect things like the PCIE GART...
62          */
63
64         /* First, the best case, the offset already lands in either the
65          * framebuffer or the GART mapped space
66          */
67         if (radeon_check_offset(dev_priv, off))
68                 return 0;
69
70         /* Ok, that didn't happen... now check if we have a zero based
71          * offset that fits in the framebuffer + gart space, apply the
72          * magic offset we get from SETPARAM or calculated from fb_location
73          */
74         if (off < (dev_priv->fb_size + dev_priv->gart_size)) {
75                 radeon_priv = file_priv->driver_priv;
76                 off += radeon_priv->radeon_fb_delta;
77         }
78
79         /* Finally, assume we aimed at a GART offset if beyond the fb */
80         if (off > fb_end)
81                 off = off - fb_end - 1 + dev_priv->gart_vm_start;
82
83         /* Now recheck and fail if out of bounds */
84         if (radeon_check_offset(dev_priv, off)) {
85                 DRM_DEBUG("offset fixed up to 0x%x\n", (unsigned int)off);
86                 *offset = off;
87                 return 0;
88         }
89         return -EINVAL;
90 }
91
92 static __inline__ int radeon_check_and_fixup_packets(drm_radeon_private_t *
93                                                      dev_priv,
94                                                      struct drm_file *file_priv,
95                                                      int id, struct drm_buffer *buf)
96 {
97         u32 *data;
98         switch (id) {
99
100         case RADEON_EMIT_PP_MISC:
101                 data = drm_buffer_pointer_to_dword(buf,
102                         (RADEON_RB3D_DEPTHOFFSET - RADEON_PP_MISC) / 4);
103
104                 if (radeon_check_and_fixup_offset(dev_priv, file_priv, data)) {
105                         DRM_ERROR("Invalid depth buffer offset\n");
106                         return -EINVAL;
107                 }
108                 break;
109
110         case RADEON_EMIT_PP_CNTL:
111                 data = drm_buffer_pointer_to_dword(buf,
112                         (RADEON_RB3D_COLOROFFSET - RADEON_PP_CNTL) / 4);
113
114                 if (radeon_check_and_fixup_offset(dev_priv, file_priv, data)) {
115                         DRM_ERROR("Invalid colour buffer offset\n");
116                         return -EINVAL;
117                 }
118                 break;
119
120         case R200_EMIT_PP_TXOFFSET_0:
121         case R200_EMIT_PP_TXOFFSET_1:
122         case R200_EMIT_PP_TXOFFSET_2:
123         case R200_EMIT_PP_TXOFFSET_3:
124         case R200_EMIT_PP_TXOFFSET_4:
125         case R200_EMIT_PP_TXOFFSET_5:
126                 data = drm_buffer_pointer_to_dword(buf, 0);
127                 if (radeon_check_and_fixup_offset(dev_priv, file_priv, data)) {
128                         DRM_ERROR("Invalid R200 texture offset\n");
129                         return -EINVAL;
130                 }
131                 break;
132
133         case RADEON_EMIT_PP_TXFILTER_0:
134         case RADEON_EMIT_PP_TXFILTER_1:
135         case RADEON_EMIT_PP_TXFILTER_2:
136                 data = drm_buffer_pointer_to_dword(buf,
137                         (RADEON_PP_TXOFFSET_0 - RADEON_PP_TXFILTER_0) / 4);
138                 if (radeon_check_and_fixup_offset(dev_priv, file_priv, data)) {
139                         DRM_ERROR("Invalid R100 texture offset\n");
140                         return -EINVAL;
141                 }
142                 break;
143
144         case R200_EMIT_PP_CUBIC_OFFSETS_0:
145         case R200_EMIT_PP_CUBIC_OFFSETS_1:
146         case R200_EMIT_PP_CUBIC_OFFSETS_2:
147         case R200_EMIT_PP_CUBIC_OFFSETS_3:
148         case R200_EMIT_PP_CUBIC_OFFSETS_4:
149         case R200_EMIT_PP_CUBIC_OFFSETS_5:{
150                         int i;
151                         for (i = 0; i < 5; i++) {
152                                 data = drm_buffer_pointer_to_dword(buf, i);
153                                 if (radeon_check_and_fixup_offset(dev_priv,
154                                                                   file_priv,
155                                                                   data)) {
156                                         DRM_ERROR
157                                             ("Invalid R200 cubic texture offset\n");
158                                         return -EINVAL;
159                                 }
160                         }
161                         break;
162                 }
163
164         case RADEON_EMIT_PP_CUBIC_OFFSETS_T0:
165         case RADEON_EMIT_PP_CUBIC_OFFSETS_T1:
166         case RADEON_EMIT_PP_CUBIC_OFFSETS_T2:{
167                         int i;
168                         for (i = 0; i < 5; i++) {
169                                 data = drm_buffer_pointer_to_dword(buf, i);
170                                 if (radeon_check_and_fixup_offset(dev_priv,
171                                                                   file_priv,
172                                                                   data)) {
173                                         DRM_ERROR
174                                             ("Invalid R100 cubic texture offset\n");
175                                         return -EINVAL;
176                                 }
177                         }
178                 }
179                 break;
180
181         case R200_EMIT_VAP_CTL:{
182                         RING_LOCALS;
183                         BEGIN_RING(2);
184                         OUT_RING_REG(RADEON_SE_TCL_STATE_FLUSH, 0);
185                         ADVANCE_RING();
186                 }
187                 break;
188
189         case RADEON_EMIT_RB3D_COLORPITCH:
190         case RADEON_EMIT_RE_LINE_PATTERN:
191         case RADEON_EMIT_SE_LINE_WIDTH:
192         case RADEON_EMIT_PP_LUM_MATRIX:
193         case RADEON_EMIT_PP_ROT_MATRIX_0:
194         case RADEON_EMIT_RB3D_STENCILREFMASK:
195         case RADEON_EMIT_SE_VPORT_XSCALE:
196         case RADEON_EMIT_SE_CNTL:
197         case RADEON_EMIT_SE_CNTL_STATUS:
198         case RADEON_EMIT_RE_MISC:
199         case RADEON_EMIT_PP_BORDER_COLOR_0:
200         case RADEON_EMIT_PP_BORDER_COLOR_1:
201         case RADEON_EMIT_PP_BORDER_COLOR_2:
202         case RADEON_EMIT_SE_ZBIAS_FACTOR:
203         case RADEON_EMIT_SE_TCL_OUTPUT_VTX_FMT:
204         case RADEON_EMIT_SE_TCL_MATERIAL_EMMISSIVE_RED:
205         case R200_EMIT_PP_TXCBLEND_0:
206         case R200_EMIT_PP_TXCBLEND_1:
207         case R200_EMIT_PP_TXCBLEND_2:
208         case R200_EMIT_PP_TXCBLEND_3:
209         case R200_EMIT_PP_TXCBLEND_4:
210         case R200_EMIT_PP_TXCBLEND_5:
211         case R200_EMIT_PP_TXCBLEND_6:
212         case R200_EMIT_PP_TXCBLEND_7:
213         case R200_EMIT_TCL_LIGHT_MODEL_CTL_0:
214         case R200_EMIT_TFACTOR_0:
215         case R200_EMIT_VTX_FMT_0:
216         case R200_EMIT_MATRIX_SELECT_0:
217         case R200_EMIT_TEX_PROC_CTL_2:
218         case R200_EMIT_TCL_UCP_VERT_BLEND_CTL:
219         case R200_EMIT_PP_TXFILTER_0:
220         case R200_EMIT_PP_TXFILTER_1:
221         case R200_EMIT_PP_TXFILTER_2:
222         case R200_EMIT_PP_TXFILTER_3:
223         case R200_EMIT_PP_TXFILTER_4:
224         case R200_EMIT_PP_TXFILTER_5:
225         case R200_EMIT_VTE_CNTL:
226         case R200_EMIT_OUTPUT_VTX_COMP_SEL:
227         case R200_EMIT_PP_TAM_DEBUG3:
228         case R200_EMIT_PP_CNTL_X:
229         case R200_EMIT_RB3D_DEPTHXY_OFFSET:
230         case R200_EMIT_RE_AUX_SCISSOR_CNTL:
231         case R200_EMIT_RE_SCISSOR_TL_0:
232         case R200_EMIT_RE_SCISSOR_TL_1:
233         case R200_EMIT_RE_SCISSOR_TL_2:
234         case R200_EMIT_SE_VAP_CNTL_STATUS:
235         case R200_EMIT_SE_VTX_STATE_CNTL:
236         case R200_EMIT_RE_POINTSIZE:
237         case R200_EMIT_TCL_INPUT_VTX_VECTOR_ADDR_0:
238         case R200_EMIT_PP_CUBIC_FACES_0:
239         case R200_EMIT_PP_CUBIC_FACES_1:
240         case R200_EMIT_PP_CUBIC_FACES_2:
241         case R200_EMIT_PP_CUBIC_FACES_3:
242         case R200_EMIT_PP_CUBIC_FACES_4:
243         case R200_EMIT_PP_CUBIC_FACES_5:
244         case RADEON_EMIT_PP_TEX_SIZE_0:
245         case RADEON_EMIT_PP_TEX_SIZE_1:
246         case RADEON_EMIT_PP_TEX_SIZE_2:
247         case R200_EMIT_RB3D_BLENDCOLOR:
248         case R200_EMIT_TCL_POINT_SPRITE_CNTL:
249         case RADEON_EMIT_PP_CUBIC_FACES_0:
250         case RADEON_EMIT_PP_CUBIC_FACES_1:
251         case RADEON_EMIT_PP_CUBIC_FACES_2:
252         case R200_EMIT_PP_TRI_PERF_CNTL:
253         case R200_EMIT_PP_AFS_0:
254         case R200_EMIT_PP_AFS_1:
255         case R200_EMIT_ATF_TFACTOR:
256         case R200_EMIT_PP_TXCTLALL_0:
257         case R200_EMIT_PP_TXCTLALL_1:
258         case R200_EMIT_PP_TXCTLALL_2:
259         case R200_EMIT_PP_TXCTLALL_3:
260         case R200_EMIT_PP_TXCTLALL_4:
261         case R200_EMIT_PP_TXCTLALL_5:
262         case R200_EMIT_VAP_PVS_CNTL:
263                 /* These packets don't contain memory offsets */
264                 break;
265
266         default:
267                 DRM_ERROR("Unknown state packet ID %d\n", id);
268                 return -EINVAL;
269         }
270
271         return 0;
272 }
273
274 static __inline__ int radeon_check_and_fixup_packet3(drm_radeon_private_t *
275                                                      dev_priv,
276                                                      struct drm_file *file_priv,
277                                                      drm_radeon_kcmd_buffer_t *
278                                                      cmdbuf,
279                                                      unsigned int *cmdsz)
280 {
281         u32 *cmd = drm_buffer_pointer_to_dword(cmdbuf->buffer, 0);
282         u32 offset, narrays;
283         int count, i, k;
284
285         count = ((*cmd & RADEON_CP_PACKET_COUNT_MASK) >> 16);
286         *cmdsz = 2 + count;
287
288         if ((*cmd & 0xc0000000) != RADEON_CP_PACKET3) {
289                 DRM_ERROR("Not a type 3 packet\n");
290                 return -EINVAL;
291         }
292
293         if (4 * *cmdsz > drm_buffer_unprocessed(cmdbuf->buffer)) {
294                 DRM_ERROR("Packet size larger than size of data provided\n");
295                 return -EINVAL;
296         }
297
298         switch (*cmd & 0xff00) {
299         /* XXX Are there old drivers needing other packets? */
300
301         case RADEON_3D_DRAW_IMMD:
302         case RADEON_3D_DRAW_VBUF:
303         case RADEON_3D_DRAW_INDX:
304         case RADEON_WAIT_FOR_IDLE:
305         case RADEON_CP_NOP:
306         case RADEON_3D_CLEAR_ZMASK:
307 /*      case RADEON_CP_NEXT_CHAR:
308         case RADEON_CP_PLY_NEXTSCAN:
309         case RADEON_CP_SET_SCISSORS: */ /* probably safe but will never need them? */
310                 /* these packets are safe */
311                 break;
312
313         case RADEON_CP_3D_DRAW_IMMD_2:
314         case RADEON_CP_3D_DRAW_VBUF_2:
315         case RADEON_CP_3D_DRAW_INDX_2:
316         case RADEON_3D_CLEAR_HIZ:
317                 /* safe but r200 only */
318                 if (dev_priv->microcode_version != UCODE_R200) {
319                         DRM_ERROR("Invalid 3d packet for r100-class chip\n");
320                         return -EINVAL;
321                 }
322                 break;
323
324         case RADEON_3D_LOAD_VBPNTR:
325
326                 if (count > 18) { /* 12 arrays max */
327                         DRM_ERROR("Too large payload in 3D_LOAD_VBPNTR (count=%d)\n",
328                                   count);
329                         return -EINVAL;
330                 }
331
332                 /* carefully check packet contents */
333                 cmd = drm_buffer_pointer_to_dword(cmdbuf->buffer, 1);
334
335                 narrays = *cmd & ~0xc000;
336                 k = 0;
337                 i = 2;
338                 while ((k < narrays) && (i < (count + 2))) {
339                         i++;            /* skip attribute field */
340                         cmd = drm_buffer_pointer_to_dword(cmdbuf->buffer, i);
341                         if (radeon_check_and_fixup_offset(dev_priv, file_priv,
342                                                           cmd)) {
343                                 DRM_ERROR
344                                     ("Invalid offset (k=%d i=%d) in 3D_LOAD_VBPNTR packet.\n",
345                                      k, i);
346                                 return -EINVAL;
347                         }
348                         k++;
349                         i++;
350                         if (k == narrays)
351                                 break;
352                         /* have one more to process, they come in pairs */
353                         cmd = drm_buffer_pointer_to_dword(cmdbuf->buffer, i);
354
355                         if (radeon_check_and_fixup_offset(dev_priv,
356                                                           file_priv, cmd))
357                         {
358                                 DRM_ERROR
359                                     ("Invalid offset (k=%d i=%d) in 3D_LOAD_VBPNTR packet.\n",
360                                      k, i);
361                                 return -EINVAL;
362                         }
363                         k++;
364                         i++;
365                 }
366                 /* do the counts match what we expect ? */
367                 if ((k != narrays) || (i != (count + 2))) {
368                         DRM_ERROR
369                             ("Malformed 3D_LOAD_VBPNTR packet (k=%d i=%d narrays=%d count+1=%d).\n",
370                               k, i, narrays, count + 1);
371                         return -EINVAL;
372                 }
373                 break;
374
375         case RADEON_3D_RNDR_GEN_INDX_PRIM:
376                 if (dev_priv->microcode_version != UCODE_R100) {
377                         DRM_ERROR("Invalid 3d packet for r200-class chip\n");
378                         return -EINVAL;
379                 }
380
381                 cmd = drm_buffer_pointer_to_dword(cmdbuf->buffer, 1);
382                 if (radeon_check_and_fixup_offset(dev_priv, file_priv, cmd)) {
383                                 DRM_ERROR("Invalid rndr_gen_indx offset\n");
384                                 return -EINVAL;
385                 }
386                 break;
387
388         case RADEON_CP_INDX_BUFFER:
389                 if (dev_priv->microcode_version != UCODE_R200) {
390                         DRM_ERROR("Invalid 3d packet for r100-class chip\n");
391                         return -EINVAL;
392                 }
393
394                 cmd = drm_buffer_pointer_to_dword(cmdbuf->buffer, 1);
395                 if ((*cmd & 0x8000ffff) != 0x80000810) {
396                         DRM_ERROR("Invalid indx_buffer reg address %08X\n", *cmd);
397                         return -EINVAL;
398                 }
399                 cmd = drm_buffer_pointer_to_dword(cmdbuf->buffer, 2);
400                 if (radeon_check_and_fixup_offset(dev_priv, file_priv, cmd)) {
401                         DRM_ERROR("Invalid indx_buffer offset is %08X\n", *cmd);
402                         return -EINVAL;
403                 }
404                 break;
405
406         case RADEON_CNTL_HOSTDATA_BLT:
407         case RADEON_CNTL_PAINT_MULTI:
408         case RADEON_CNTL_BITBLT_MULTI:
409                 /* MSB of opcode: next DWORD GUI_CNTL */
410                 cmd = drm_buffer_pointer_to_dword(cmdbuf->buffer, 1);
411                 if (*cmd & (RADEON_GMC_SRC_PITCH_OFFSET_CNTL
412                               | RADEON_GMC_DST_PITCH_OFFSET_CNTL)) {
413                         u32 *cmd2 = drm_buffer_pointer_to_dword(cmdbuf->buffer, 2);
414                         offset = *cmd2 << 10;
415                         if (radeon_check_and_fixup_offset
416                             (dev_priv, file_priv, &offset)) {
417                                 DRM_ERROR("Invalid first packet offset\n");
418                                 return -EINVAL;
419                         }
420                         *cmd2 = (*cmd2 & 0xffc00000) | offset >> 10;
421                 }
422
423                 if ((*cmd & RADEON_GMC_SRC_PITCH_OFFSET_CNTL) &&
424                     (*cmd & RADEON_GMC_DST_PITCH_OFFSET_CNTL)) {
425                         u32 *cmd3 = drm_buffer_pointer_to_dword(cmdbuf->buffer, 3);
426                         offset = *cmd << 10;
427                         if (radeon_check_and_fixup_offset
428                             (dev_priv, file_priv, &offset)) {
429                                 DRM_ERROR("Invalid second packet offset\n");
430                                 return -EINVAL;
431                         }
432                         *cmd3 = (*cmd3 & 0xffc00000) | offset >> 10;
433                 }
434                 break;
435
436         default:
437                 DRM_ERROR("Invalid packet type %x\n", *cmd & 0xff00);
438                 return -EINVAL;
439         }
440
441         return 0;
442 }
443
444 /* ================================================================
445  * CP hardware state programming functions
446  */
447
448 static __inline__ void radeon_emit_clip_rect(drm_radeon_private_t * dev_priv,
449                                              struct drm_clip_rect * box)
450 {
451         RING_LOCALS;
452
453         DRM_DEBUG("   box:  x1=%d y1=%d  x2=%d y2=%d\n",
454                   box->x1, box->y1, box->x2, box->y2);
455
456         BEGIN_RING(4);
457         OUT_RING(CP_PACKET0(RADEON_RE_TOP_LEFT, 0));
458         OUT_RING((box->y1 << 16) | box->x1);
459         OUT_RING(CP_PACKET0(RADEON_RE_WIDTH_HEIGHT, 0));
460         OUT_RING(((box->y2 - 1) << 16) | (box->x2 - 1));
461         ADVANCE_RING();
462 }
463
464 /* Emit 1.1 state
465  */
466 static int radeon_emit_state(drm_radeon_private_t * dev_priv,
467                              struct drm_file *file_priv,
468                              drm_radeon_context_regs_t * ctx,
469                              drm_radeon_texture_regs_t * tex,
470                              unsigned int dirty)
471 {
472         RING_LOCALS;
473         DRM_DEBUG("dirty=0x%08x\n", dirty);
474
475         if (dirty & RADEON_UPLOAD_CONTEXT) {
476                 if (radeon_check_and_fixup_offset(dev_priv, file_priv,
477                                                   &ctx->rb3d_depthoffset)) {
478                         DRM_ERROR("Invalid depth buffer offset\n");
479                         return -EINVAL;
480                 }
481
482                 if (radeon_check_and_fixup_offset(dev_priv, file_priv,
483                                                   &ctx->rb3d_coloroffset)) {
484                         DRM_ERROR("Invalid depth buffer offset\n");
485                         return -EINVAL;
486                 }
487
488                 BEGIN_RING(14);
489                 OUT_RING(CP_PACKET0(RADEON_PP_MISC, 6));
490                 OUT_RING(ctx->pp_misc);
491                 OUT_RING(ctx->pp_fog_color);
492                 OUT_RING(ctx->re_solid_color);
493                 OUT_RING(ctx->rb3d_blendcntl);
494                 OUT_RING(ctx->rb3d_depthoffset);
495                 OUT_RING(ctx->rb3d_depthpitch);
496                 OUT_RING(ctx->rb3d_zstencilcntl);
497                 OUT_RING(CP_PACKET0(RADEON_PP_CNTL, 2));
498                 OUT_RING(ctx->pp_cntl);
499                 OUT_RING(ctx->rb3d_cntl);
500                 OUT_RING(ctx->rb3d_coloroffset);
501                 OUT_RING(CP_PACKET0(RADEON_RB3D_COLORPITCH, 0));
502                 OUT_RING(ctx->rb3d_colorpitch);
503                 ADVANCE_RING();
504         }
505
506         if (dirty & RADEON_UPLOAD_VERTFMT) {
507                 BEGIN_RING(2);
508                 OUT_RING(CP_PACKET0(RADEON_SE_COORD_FMT, 0));
509                 OUT_RING(ctx->se_coord_fmt);
510                 ADVANCE_RING();
511         }
512
513         if (dirty & RADEON_UPLOAD_LINE) {
514                 BEGIN_RING(5);
515                 OUT_RING(CP_PACKET0(RADEON_RE_LINE_PATTERN, 1));
516                 OUT_RING(ctx->re_line_pattern);
517                 OUT_RING(ctx->re_line_state);
518                 OUT_RING(CP_PACKET0(RADEON_SE_LINE_WIDTH, 0));
519                 OUT_RING(ctx->se_line_width);
520                 ADVANCE_RING();
521         }
522
523         if (dirty & RADEON_UPLOAD_BUMPMAP) {
524                 BEGIN_RING(5);
525                 OUT_RING(CP_PACKET0(RADEON_PP_LUM_MATRIX, 0));
526                 OUT_RING(ctx->pp_lum_matrix);
527                 OUT_RING(CP_PACKET0(RADEON_PP_ROT_MATRIX_0, 1));
528                 OUT_RING(ctx->pp_rot_matrix_0);
529                 OUT_RING(ctx->pp_rot_matrix_1);
530                 ADVANCE_RING();
531         }
532
533         if (dirty & RADEON_UPLOAD_MASKS) {
534                 BEGIN_RING(4);
535                 OUT_RING(CP_PACKET0(RADEON_RB3D_STENCILREFMASK, 2));
536                 OUT_RING(ctx->rb3d_stencilrefmask);
537                 OUT_RING(ctx->rb3d_ropcntl);
538                 OUT_RING(ctx->rb3d_planemask);
539                 ADVANCE_RING();
540         }
541
542         if (dirty & RADEON_UPLOAD_VIEWPORT) {
543                 BEGIN_RING(7);
544                 OUT_RING(CP_PACKET0(RADEON_SE_VPORT_XSCALE, 5));
545                 OUT_RING(ctx->se_vport_xscale);
546                 OUT_RING(ctx->se_vport_xoffset);
547                 OUT_RING(ctx->se_vport_yscale);
548                 OUT_RING(ctx->se_vport_yoffset);
549                 OUT_RING(ctx->se_vport_zscale);
550                 OUT_RING(ctx->se_vport_zoffset);
551                 ADVANCE_RING();
552         }
553
554         if (dirty & RADEON_UPLOAD_SETUP) {
555                 BEGIN_RING(4);
556                 OUT_RING(CP_PACKET0(RADEON_SE_CNTL, 0));
557                 OUT_RING(ctx->se_cntl);
558                 OUT_RING(CP_PACKET0(RADEON_SE_CNTL_STATUS, 0));
559                 OUT_RING(ctx->se_cntl_status);
560                 ADVANCE_RING();
561         }
562
563         if (dirty & RADEON_UPLOAD_MISC) {
564                 BEGIN_RING(2);
565                 OUT_RING(CP_PACKET0(RADEON_RE_MISC, 0));
566                 OUT_RING(ctx->re_misc);
567                 ADVANCE_RING();
568         }
569
570         if (dirty & RADEON_UPLOAD_TEX0) {
571                 if (radeon_check_and_fixup_offset(dev_priv, file_priv,
572                                                   &tex[0].pp_txoffset)) {
573                         DRM_ERROR("Invalid texture offset for unit 0\n");
574                         return -EINVAL;
575                 }
576
577                 BEGIN_RING(9);
578                 OUT_RING(CP_PACKET0(RADEON_PP_TXFILTER_0, 5));
579                 OUT_RING(tex[0].pp_txfilter);
580                 OUT_RING(tex[0].pp_txformat);
581                 OUT_RING(tex[0].pp_txoffset);
582                 OUT_RING(tex[0].pp_txcblend);
583                 OUT_RING(tex[0].pp_txablend);
584                 OUT_RING(tex[0].pp_tfactor);
585                 OUT_RING(CP_PACKET0(RADEON_PP_BORDER_COLOR_0, 0));
586                 OUT_RING(tex[0].pp_border_color);
587                 ADVANCE_RING();
588         }
589
590         if (dirty & RADEON_UPLOAD_TEX1) {
591                 if (radeon_check_and_fixup_offset(dev_priv, file_priv,
592                                                   &tex[1].pp_txoffset)) {
593                         DRM_ERROR("Invalid texture offset for unit 1\n");
594                         return -EINVAL;
595                 }
596
597                 BEGIN_RING(9);
598                 OUT_RING(CP_PACKET0(RADEON_PP_TXFILTER_1, 5));
599                 OUT_RING(tex[1].pp_txfilter);
600                 OUT_RING(tex[1].pp_txformat);
601                 OUT_RING(tex[1].pp_txoffset);
602                 OUT_RING(tex[1].pp_txcblend);
603                 OUT_RING(tex[1].pp_txablend);
604                 OUT_RING(tex[1].pp_tfactor);
605                 OUT_RING(CP_PACKET0(RADEON_PP_BORDER_COLOR_1, 0));
606                 OUT_RING(tex[1].pp_border_color);
607                 ADVANCE_RING();
608         }
609
610         if (dirty & RADEON_UPLOAD_TEX2) {
611                 if (radeon_check_and_fixup_offset(dev_priv, file_priv,
612                                                   &tex[2].pp_txoffset)) {
613                         DRM_ERROR("Invalid texture offset for unit 2\n");
614                         return -EINVAL;
615                 }
616
617                 BEGIN_RING(9);
618                 OUT_RING(CP_PACKET0(RADEON_PP_TXFILTER_2, 5));
619                 OUT_RING(tex[2].pp_txfilter);
620                 OUT_RING(tex[2].pp_txformat);
621                 OUT_RING(tex[2].pp_txoffset);
622                 OUT_RING(tex[2].pp_txcblend);
623                 OUT_RING(tex[2].pp_txablend);
624                 OUT_RING(tex[2].pp_tfactor);
625                 OUT_RING(CP_PACKET0(RADEON_PP_BORDER_COLOR_2, 0));
626                 OUT_RING(tex[2].pp_border_color);
627                 ADVANCE_RING();
628         }
629
630         return 0;
631 }
632
633 /* Emit 1.2 state
634  */
635 static int radeon_emit_state2(drm_radeon_private_t * dev_priv,
636                               struct drm_file *file_priv,
637                               drm_radeon_state_t * state)
638 {
639         RING_LOCALS;
640
641         if (state->dirty & RADEON_UPLOAD_ZBIAS) {
642                 BEGIN_RING(3);
643                 OUT_RING(CP_PACKET0(RADEON_SE_ZBIAS_FACTOR, 1));
644                 OUT_RING(state->context2.se_zbias_factor);
645                 OUT_RING(state->context2.se_zbias_constant);
646                 ADVANCE_RING();
647         }
648
649         return radeon_emit_state(dev_priv, file_priv, &state->context,
650                                  state->tex, state->dirty);
651 }
652
653 /* New (1.3) state mechanism.  3 commands (packet, scalar, vector) in
654  * 1.3 cmdbuffers allow all previous state to be updated as well as
655  * the tcl scalar and vector areas.
656  */
657 static struct {
658         int start;
659         int len;
660         const char *name;
661 } packet[RADEON_MAX_STATE_PACKETS] = {
662         {RADEON_PP_MISC, 7, "RADEON_PP_MISC"},
663         {RADEON_PP_CNTL, 3, "RADEON_PP_CNTL"},
664         {RADEON_RB3D_COLORPITCH, 1, "RADEON_RB3D_COLORPITCH"},
665         {RADEON_RE_LINE_PATTERN, 2, "RADEON_RE_LINE_PATTERN"},
666         {RADEON_SE_LINE_WIDTH, 1, "RADEON_SE_LINE_WIDTH"},
667         {RADEON_PP_LUM_MATRIX, 1, "RADEON_PP_LUM_MATRIX"},
668         {RADEON_PP_ROT_MATRIX_0, 2, "RADEON_PP_ROT_MATRIX_0"},
669         {RADEON_RB3D_STENCILREFMASK, 3, "RADEON_RB3D_STENCILREFMASK"},
670         {RADEON_SE_VPORT_XSCALE, 6, "RADEON_SE_VPORT_XSCALE"},
671         {RADEON_SE_CNTL, 2, "RADEON_SE_CNTL"},
672         {RADEON_SE_CNTL_STATUS, 1, "RADEON_SE_CNTL_STATUS"},
673         {RADEON_RE_MISC, 1, "RADEON_RE_MISC"},
674         {RADEON_PP_TXFILTER_0, 6, "RADEON_PP_TXFILTER_0"},
675         {RADEON_PP_BORDER_COLOR_0, 1, "RADEON_PP_BORDER_COLOR_0"},
676         {RADEON_PP_TXFILTER_1, 6, "RADEON_PP_TXFILTER_1"},
677         {RADEON_PP_BORDER_COLOR_1, 1, "RADEON_PP_BORDER_COLOR_1"},
678         {RADEON_PP_TXFILTER_2, 6, "RADEON_PP_TXFILTER_2"},
679         {RADEON_PP_BORDER_COLOR_2, 1, "RADEON_PP_BORDER_COLOR_2"},
680         {RADEON_SE_ZBIAS_FACTOR, 2, "RADEON_SE_ZBIAS_FACTOR"},
681         {RADEON_SE_TCL_OUTPUT_VTX_FMT, 11, "RADEON_SE_TCL_OUTPUT_VTX_FMT"},
682         {RADEON_SE_TCL_MATERIAL_EMMISSIVE_RED, 17,
683                     "RADEON_SE_TCL_MATERIAL_EMMISSIVE_RED"},
684         {R200_PP_TXCBLEND_0, 4, "R200_PP_TXCBLEND_0"},
685         {R200_PP_TXCBLEND_1, 4, "R200_PP_TXCBLEND_1"},
686         {R200_PP_TXCBLEND_2, 4, "R200_PP_TXCBLEND_2"},
687         {R200_PP_TXCBLEND_3, 4, "R200_PP_TXCBLEND_3"},
688         {R200_PP_TXCBLEND_4, 4, "R200_PP_TXCBLEND_4"},
689         {R200_PP_TXCBLEND_5, 4, "R200_PP_TXCBLEND_5"},
690         {R200_PP_TXCBLEND_6, 4, "R200_PP_TXCBLEND_6"},
691         {R200_PP_TXCBLEND_7, 4, "R200_PP_TXCBLEND_7"},
692         {R200_SE_TCL_LIGHT_MODEL_CTL_0, 6, "R200_SE_TCL_LIGHT_MODEL_CTL_0"},
693         {R200_PP_TFACTOR_0, 6, "R200_PP_TFACTOR_0"},
694         {R200_SE_VTX_FMT_0, 4, "R200_SE_VTX_FMT_0"},
695         {R200_SE_VAP_CNTL, 1, "R200_SE_VAP_CNTL"},
696         {R200_SE_TCL_MATRIX_SEL_0, 5, "R200_SE_TCL_MATRIX_SEL_0"},
697         {R200_SE_TCL_TEX_PROC_CTL_2, 5, "R200_SE_TCL_TEX_PROC_CTL_2"},
698         {R200_SE_TCL_UCP_VERT_BLEND_CTL, 1, "R200_SE_TCL_UCP_VERT_BLEND_CTL"},
699         {R200_PP_TXFILTER_0, 6, "R200_PP_TXFILTER_0"},
700         {R200_PP_TXFILTER_1, 6, "R200_PP_TXFILTER_1"},
701         {R200_PP_TXFILTER_2, 6, "R200_PP_TXFILTER_2"},
702         {R200_PP_TXFILTER_3, 6, "R200_PP_TXFILTER_3"},
703         {R200_PP_TXFILTER_4, 6, "R200_PP_TXFILTER_4"},
704         {R200_PP_TXFILTER_5, 6, "R200_PP_TXFILTER_5"},
705         {R200_PP_TXOFFSET_0, 1, "R200_PP_TXOFFSET_0"},
706         {R200_PP_TXOFFSET_1, 1, "R200_PP_TXOFFSET_1"},
707         {R200_PP_TXOFFSET_2, 1, "R200_PP_TXOFFSET_2"},
708         {R200_PP_TXOFFSET_3, 1, "R200_PP_TXOFFSET_3"},
709         {R200_PP_TXOFFSET_4, 1, "R200_PP_TXOFFSET_4"},
710         {R200_PP_TXOFFSET_5, 1, "R200_PP_TXOFFSET_5"},
711         {R200_SE_VTE_CNTL, 1, "R200_SE_VTE_CNTL"},
712         {R200_SE_TCL_OUTPUT_VTX_COMP_SEL, 1,
713          "R200_SE_TCL_OUTPUT_VTX_COMP_SEL"},
714         {R200_PP_TAM_DEBUG3, 1, "R200_PP_TAM_DEBUG3"},
715         {R200_PP_CNTL_X, 1, "R200_PP_CNTL_X"},
716         {R200_RB3D_DEPTHXY_OFFSET, 1, "R200_RB3D_DEPTHXY_OFFSET"},
717         {R200_RE_AUX_SCISSOR_CNTL, 1, "R200_RE_AUX_SCISSOR_CNTL"},
718         {R200_RE_SCISSOR_TL_0, 2, "R200_RE_SCISSOR_TL_0"},
719         {R200_RE_SCISSOR_TL_1, 2, "R200_RE_SCISSOR_TL_1"},
720         {R200_RE_SCISSOR_TL_2, 2, "R200_RE_SCISSOR_TL_2"},
721         {R200_SE_VAP_CNTL_STATUS, 1, "R200_SE_VAP_CNTL_STATUS"},
722         {R200_SE_VTX_STATE_CNTL, 1, "R200_SE_VTX_STATE_CNTL"},
723         {R200_RE_POINTSIZE, 1, "R200_RE_POINTSIZE"},
724         {R200_SE_TCL_INPUT_VTX_VECTOR_ADDR_0, 4,
725                     "R200_SE_TCL_INPUT_VTX_VECTOR_ADDR_0"},
726         {R200_PP_CUBIC_FACES_0, 1, "R200_PP_CUBIC_FACES_0"},    /* 61 */
727         {R200_PP_CUBIC_OFFSET_F1_0, 5, "R200_PP_CUBIC_OFFSET_F1_0"}, /* 62 */
728         {R200_PP_CUBIC_FACES_1, 1, "R200_PP_CUBIC_FACES_1"},
729         {R200_PP_CUBIC_OFFSET_F1_1, 5, "R200_PP_CUBIC_OFFSET_F1_1"},
730         {R200_PP_CUBIC_FACES_2, 1, "R200_PP_CUBIC_FACES_2"},
731         {R200_PP_CUBIC_OFFSET_F1_2, 5, "R200_PP_CUBIC_OFFSET_F1_2"},
732         {R200_PP_CUBIC_FACES_3, 1, "R200_PP_CUBIC_FACES_3"},
733         {R200_PP_CUBIC_OFFSET_F1_3, 5, "R200_PP_CUBIC_OFFSET_F1_3"},
734         {R200_PP_CUBIC_FACES_4, 1, "R200_PP_CUBIC_FACES_4"},
735         {R200_PP_CUBIC_OFFSET_F1_4, 5, "R200_PP_CUBIC_OFFSET_F1_4"},
736         {R200_PP_CUBIC_FACES_5, 1, "R200_PP_CUBIC_FACES_5"},
737         {R200_PP_CUBIC_OFFSET_F1_5, 5, "R200_PP_CUBIC_OFFSET_F1_5"},
738         {RADEON_PP_TEX_SIZE_0, 2, "RADEON_PP_TEX_SIZE_0"},
739         {RADEON_PP_TEX_SIZE_1, 2, "RADEON_PP_TEX_SIZE_1"},
740         {RADEON_PP_TEX_SIZE_2, 2, "RADEON_PP_TEX_SIZE_2"},
741         {R200_RB3D_BLENDCOLOR, 3, "R200_RB3D_BLENDCOLOR"},
742         {R200_SE_TCL_POINT_SPRITE_CNTL, 1, "R200_SE_TCL_POINT_SPRITE_CNTL"},
743         {RADEON_PP_CUBIC_FACES_0, 1, "RADEON_PP_CUBIC_FACES_0"},
744         {RADEON_PP_CUBIC_OFFSET_T0_0, 5, "RADEON_PP_CUBIC_OFFSET_T0_0"},
745         {RADEON_PP_CUBIC_FACES_1, 1, "RADEON_PP_CUBIC_FACES_1"},
746         {RADEON_PP_CUBIC_OFFSET_T1_0, 5, "RADEON_PP_CUBIC_OFFSET_T1_0"},
747         {RADEON_PP_CUBIC_FACES_2, 1, "RADEON_PP_CUBIC_FACES_2"},
748         {RADEON_PP_CUBIC_OFFSET_T2_0, 5, "RADEON_PP_CUBIC_OFFSET_T2_0"},
749         {R200_PP_TRI_PERF, 2, "R200_PP_TRI_PERF"},
750         {R200_PP_AFS_0, 32, "R200_PP_AFS_0"},     /* 85 */
751         {R200_PP_AFS_1, 32, "R200_PP_AFS_1"},
752         {R200_PP_TFACTOR_0, 8, "R200_ATF_TFACTOR"},
753         {R200_PP_TXFILTER_0, 8, "R200_PP_TXCTLALL_0"},
754         {R200_PP_TXFILTER_1, 8, "R200_PP_TXCTLALL_1"},
755         {R200_PP_TXFILTER_2, 8, "R200_PP_TXCTLALL_2"},
756         {R200_PP_TXFILTER_3, 8, "R200_PP_TXCTLALL_3"},
757         {R200_PP_TXFILTER_4, 8, "R200_PP_TXCTLALL_4"},
758         {R200_PP_TXFILTER_5, 8, "R200_PP_TXCTLALL_5"},
759         {R200_VAP_PVS_CNTL_1, 2, "R200_VAP_PVS_CNTL"},
760 };
761
762 /* ================================================================
763  * Performance monitoring functions
764  */
765
766 static void radeon_clear_box(drm_radeon_private_t * dev_priv,
767                              struct drm_radeon_master_private *master_priv,
768                              int x, int y, int w, int h, int r, int g, int b)
769 {
770         u32 color;
771         RING_LOCALS;
772
773         x += master_priv->sarea_priv->boxes[0].x1;
774         y += master_priv->sarea_priv->boxes[0].y1;
775
776         switch (dev_priv->color_fmt) {
777         case RADEON_COLOR_FORMAT_RGB565:
778                 color = (((r & 0xf8) << 8) |
779                          ((g & 0xfc) << 3) | ((b & 0xf8) >> 3));
780                 break;
781         case RADEON_COLOR_FORMAT_ARGB8888:
782         default:
783                 color = (((0xff) << 24) | (r << 16) | (g << 8) | b);
784                 break;
785         }
786
787         BEGIN_RING(4);
788         RADEON_WAIT_UNTIL_3D_IDLE();
789         OUT_RING(CP_PACKET0(RADEON_DP_WRITE_MASK, 0));
790         OUT_RING(0xffffffff);
791         ADVANCE_RING();
792
793         BEGIN_RING(6);
794
795         OUT_RING(CP_PACKET3(RADEON_CNTL_PAINT_MULTI, 4));
796         OUT_RING(RADEON_GMC_DST_PITCH_OFFSET_CNTL |
797                  RADEON_GMC_BRUSH_SOLID_COLOR |
798                  (dev_priv->color_fmt << 8) |
799                  RADEON_GMC_SRC_DATATYPE_COLOR |
800                  RADEON_ROP3_P | RADEON_GMC_CLR_CMP_CNTL_DIS);
801
802         if (master_priv->sarea_priv->pfCurrentPage == 1) {
803                 OUT_RING(dev_priv->front_pitch_offset);
804         } else {
805                 OUT_RING(dev_priv->back_pitch_offset);
806         }
807
808         OUT_RING(color);
809
810         OUT_RING((x << 16) | y);
811         OUT_RING((w << 16) | h);
812
813         ADVANCE_RING();
814 }
815
816 static void radeon_cp_performance_boxes(drm_radeon_private_t *dev_priv, struct drm_radeon_master_private *master_priv)
817 {
818         /* Collapse various things into a wait flag -- trying to
819          * guess if userspase slept -- better just to have them tell us.
820          */
821         if (dev_priv->stats.last_frame_reads > 1 ||
822             dev_priv->stats.last_clear_reads > dev_priv->stats.clears) {
823                 dev_priv->stats.boxes |= RADEON_BOX_WAIT_IDLE;
824         }
825
826         if (dev_priv->stats.freelist_loops) {
827                 dev_priv->stats.boxes |= RADEON_BOX_WAIT_IDLE;
828         }
829
830         /* Purple box for page flipping
831          */
832         if (dev_priv->stats.boxes & RADEON_BOX_FLIP)
833                 radeon_clear_box(dev_priv, master_priv, 4, 4, 8, 8, 255, 0, 255);
834
835         /* Red box if we have to wait for idle at any point
836          */
837         if (dev_priv->stats.boxes & RADEON_BOX_WAIT_IDLE)
838                 radeon_clear_box(dev_priv, master_priv, 16, 4, 8, 8, 255, 0, 0);
839
840         /* Blue box: lost context?
841          */
842
843         /* Yellow box for texture swaps
844          */
845         if (dev_priv->stats.boxes & RADEON_BOX_TEXTURE_LOAD)
846                 radeon_clear_box(dev_priv, master_priv, 40, 4, 8, 8, 255, 255, 0);
847
848         /* Green box if hardware never idles (as far as we can tell)
849          */
850         if (!(dev_priv->stats.boxes & RADEON_BOX_DMA_IDLE))
851                 radeon_clear_box(dev_priv, master_priv, 64, 4, 8, 8, 0, 255, 0);
852
853         /* Draw bars indicating number of buffers allocated
854          * (not a great measure, easily confused)
855          */
856         if (dev_priv->stats.requested_bufs) {
857                 if (dev_priv->stats.requested_bufs > 100)
858                         dev_priv->stats.requested_bufs = 100;
859
860                 radeon_clear_box(dev_priv, master_priv, 4, 16,
861                                  dev_priv->stats.requested_bufs, 4,
862                                  196, 128, 128);
863         }
864
865         memset(&dev_priv->stats, 0, sizeof(dev_priv->stats));
866
867 }
868
869 /* ================================================================
870  * CP command dispatch functions
871  */
872
873 static void radeon_cp_dispatch_clear(struct drm_device * dev,
874                                      struct drm_master *master,
875                                      drm_radeon_clear_t * clear,
876                                      drm_radeon_clear_rect_t * depth_boxes)
877 {
878         drm_radeon_private_t *dev_priv = dev->dev_private;
879         struct drm_radeon_master_private *master_priv = master->driver_priv;
880         drm_radeon_sarea_t *sarea_priv = master_priv->sarea_priv;
881         drm_radeon_depth_clear_t *depth_clear = &dev_priv->depth_clear;
882         int nbox = sarea_priv->nbox;
883         struct drm_clip_rect *pbox = sarea_priv->boxes;
884         unsigned int flags = clear->flags;
885         u32 rb3d_cntl = 0, rb3d_stencilrefmask = 0;
886         int i;
887         RING_LOCALS;
888         DRM_DEBUG("flags = 0x%x\n", flags);
889
890         dev_priv->stats.clears++;
891
892         if (sarea_priv->pfCurrentPage == 1) {
893                 unsigned int tmp = flags;
894
895                 flags &= ~(RADEON_FRONT | RADEON_BACK);
896                 if (tmp & RADEON_FRONT)
897                         flags |= RADEON_BACK;
898                 if (tmp & RADEON_BACK)
899                         flags |= RADEON_FRONT;
900         }
901
902         if (flags & (RADEON_FRONT | RADEON_BACK)) {
903
904                 BEGIN_RING(4);
905
906                 /* Ensure the 3D stream is idle before doing a
907                  * 2D fill to clear the front or back buffer.
908                  */
909                 RADEON_WAIT_UNTIL_3D_IDLE();
910
911                 OUT_RING(CP_PACKET0(RADEON_DP_WRITE_MASK, 0));
912                 OUT_RING(clear->color_mask);
913
914                 ADVANCE_RING();
915
916                 /* Make sure we restore the 3D state next time.
917                  */
918                 sarea_priv->ctx_owner = 0;
919
920                 for (i = 0; i < nbox; i++) {
921                         int x = pbox[i].x1;
922                         int y = pbox[i].y1;
923                         int w = pbox[i].x2 - x;
924                         int h = pbox[i].y2 - y;
925
926                         DRM_DEBUG("%d,%d-%d,%d flags 0x%x\n",
927                                   x, y, w, h, flags);
928
929                         if (flags & RADEON_FRONT) {
930                                 BEGIN_RING(6);
931
932                                 OUT_RING(CP_PACKET3
933                                          (RADEON_CNTL_PAINT_MULTI, 4));
934                                 OUT_RING(RADEON_GMC_DST_PITCH_OFFSET_CNTL |
935                                          RADEON_GMC_BRUSH_SOLID_COLOR |
936                                          (dev_priv->
937                                           color_fmt << 8) |
938                                          RADEON_GMC_SRC_DATATYPE_COLOR |
939                                          RADEON_ROP3_P |
940                                          RADEON_GMC_CLR_CMP_CNTL_DIS);
941
942                                 OUT_RING(dev_priv->front_pitch_offset);
943                                 OUT_RING(clear->clear_color);
944
945                                 OUT_RING((x << 16) | y);
946                                 OUT_RING((w << 16) | h);
947
948                                 ADVANCE_RING();
949                         }
950
951                         if (flags & RADEON_BACK) {
952                                 BEGIN_RING(6);
953
954                                 OUT_RING(CP_PACKET3
955                                          (RADEON_CNTL_PAINT_MULTI, 4));
956                                 OUT_RING(RADEON_GMC_DST_PITCH_OFFSET_CNTL |
957                                          RADEON_GMC_BRUSH_SOLID_COLOR |
958                                          (dev_priv->
959                                           color_fmt << 8) |
960                                          RADEON_GMC_SRC_DATATYPE_COLOR |
961                                          RADEON_ROP3_P |
962                                          RADEON_GMC_CLR_CMP_CNTL_DIS);
963
964                                 OUT_RING(dev_priv->back_pitch_offset);
965                                 OUT_RING(clear->clear_color);
966
967                                 OUT_RING((x << 16) | y);
968                                 OUT_RING((w << 16) | h);
969
970                                 ADVANCE_RING();
971                         }
972                 }
973         }
974
975         /* hyper z clear */
976         /* no docs available, based on reverse engeneering by Stephane Marchesin */
977         if ((flags & (RADEON_DEPTH | RADEON_STENCIL))
978             && (flags & RADEON_CLEAR_FASTZ)) {
979
980                 int i;
981                 int depthpixperline =
982                     dev_priv->depth_fmt ==
983                     RADEON_DEPTH_FORMAT_16BIT_INT_Z ? (dev_priv->depth_pitch /
984                                                        2) : (dev_priv->
985                                                              depth_pitch / 4);
986
987                 u32 clearmask;
988
989                 u32 tempRB3D_DEPTHCLEARVALUE = clear->clear_depth |
990                     ((clear->depth_mask & 0xff) << 24);
991
992                 /* Make sure we restore the 3D state next time.
993                  * we haven't touched any "normal" state - still need this?
994                  */
995                 sarea_priv->ctx_owner = 0;
996
997                 if ((dev_priv->flags & RADEON_HAS_HIERZ)
998                     && (flags & RADEON_USE_HIERZ)) {
999                         /* FIXME : reverse engineer that for Rx00 cards */
1000                         /* FIXME : the mask supposedly contains low-res z values. So can't set
1001                            just to the max (0xff? or actually 0x3fff?), need to take z clear
1002                            value into account? */
1003                         /* pattern seems to work for r100, though get slight
1004                            rendering errors with glxgears. If hierz is not enabled for r100,
1005                            only 4 bits which indicate clear (15,16,31,32, all zero) matter, the
1006                            other ones are ignored, and the same clear mask can be used. That's
1007                            very different behaviour than R200 which needs different clear mask
1008                            and different number of tiles to clear if hierz is enabled or not !?!
1009                          */
1010                         clearmask = (0xff << 22) | (0xff << 6) | 0x003f003f;
1011                 } else {
1012                         /* clear mask : chooses the clearing pattern.
1013                            rv250: could be used to clear only parts of macrotiles
1014                            (but that would get really complicated...)?
1015                            bit 0 and 1 (either or both of them ?!?!) are used to
1016                            not clear tile (or maybe one of the bits indicates if the tile is
1017                            compressed or not), bit 2 and 3 to not clear tile 1,...,.
1018                            Pattern is as follows:
1019                            | 0,1 | 4,5 | 8,9 |12,13|16,17|20,21|24,25|28,29|
1020                            bits -------------------------------------------------
1021                            | 2,3 | 6,7 |10,11|14,15|18,19|22,23|26,27|30,31|
1022                            rv100: clearmask covers 2x8 4x1 tiles, but one clear still
1023                            covers 256 pixels ?!?
1024                          */
1025                         clearmask = 0x0;
1026                 }
1027
1028                 BEGIN_RING(8);
1029                 RADEON_WAIT_UNTIL_2D_IDLE();
1030                 OUT_RING_REG(RADEON_RB3D_DEPTHCLEARVALUE,
1031                              tempRB3D_DEPTHCLEARVALUE);
1032                 /* what offset is this exactly ? */
1033                 OUT_RING_REG(RADEON_RB3D_ZMASKOFFSET, 0);
1034                 /* need ctlstat, otherwise get some strange black flickering */
1035                 OUT_RING_REG(RADEON_RB3D_ZCACHE_CTLSTAT,
1036                              RADEON_RB3D_ZC_FLUSH_ALL);
1037                 ADVANCE_RING();
1038
1039                 for (i = 0; i < nbox; i++) {
1040                         int tileoffset, nrtilesx, nrtilesy, j;
1041                         /* it looks like r200 needs rv-style clears, at least if hierz is not enabled? */
1042                         if ((dev_priv->flags & RADEON_HAS_HIERZ)
1043                             && !(dev_priv->microcode_version == UCODE_R200)) {
1044                                 /* FIXME : figure this out for r200 (when hierz is enabled). Or
1045                                    maybe r200 actually doesn't need to put the low-res z value into
1046                                    the tile cache like r100, but just needs to clear the hi-level z-buffer?
1047                                    Works for R100, both with hierz and without.
1048                                    R100 seems to operate on 2x1 8x8 tiles, but...
1049                                    odd: offset/nrtiles need to be 64 pix (4 block) aligned? Potentially
1050                                    problematic with resolutions which are not 64 pix aligned? */
1051                                 tileoffset =
1052                                     ((pbox[i].y1 >> 3) * depthpixperline +
1053                                      pbox[i].x1) >> 6;
1054                                 nrtilesx =
1055                                     ((pbox[i].x2 & ~63) -
1056                                      (pbox[i].x1 & ~63)) >> 4;
1057                                 nrtilesy =
1058                                     (pbox[i].y2 >> 3) - (pbox[i].y1 >> 3);
1059                                 for (j = 0; j <= nrtilesy; j++) {
1060                                         BEGIN_RING(4);
1061                                         OUT_RING(CP_PACKET3
1062                                                  (RADEON_3D_CLEAR_ZMASK, 2));
1063                                         /* first tile */
1064                                         OUT_RING(tileoffset * 8);
1065                                         /* the number of tiles to clear */
1066                                         OUT_RING(nrtilesx + 4);
1067                                         /* clear mask : chooses the clearing pattern. */
1068                                         OUT_RING(clearmask);
1069                                         ADVANCE_RING();
1070                                         tileoffset += depthpixperline >> 6;
1071                                 }
1072                         } else if (dev_priv->microcode_version == UCODE_R200) {
1073                                 /* works for rv250. */
1074                                 /* find first macro tile (8x2 4x4 z-pixels on rv250) */
1075                                 tileoffset =
1076                                     ((pbox[i].y1 >> 3) * depthpixperline +
1077                                      pbox[i].x1) >> 5;
1078                                 nrtilesx =
1079                                     (pbox[i].x2 >> 5) - (pbox[i].x1 >> 5);
1080                                 nrtilesy =
1081                                     (pbox[i].y2 >> 3) - (pbox[i].y1 >> 3);
1082                                 for (j = 0; j <= nrtilesy; j++) {
1083                                         BEGIN_RING(4);
1084                                         OUT_RING(CP_PACKET3
1085                                                  (RADEON_3D_CLEAR_ZMASK, 2));
1086                                         /* first tile */
1087                                         /* judging by the first tile offset needed, could possibly
1088                                            directly address/clear 4x4 tiles instead of 8x2 * 4x4
1089                                            macro tiles, though would still need clear mask for
1090                                            right/bottom if truely 4x4 granularity is desired ? */
1091                                         OUT_RING(tileoffset * 16);
1092                                         /* the number of tiles to clear */
1093                                         OUT_RING(nrtilesx + 1);
1094                                         /* clear mask : chooses the clearing pattern. */
1095                                         OUT_RING(clearmask);
1096                                         ADVANCE_RING();
1097                                         tileoffset += depthpixperline >> 5;
1098                                 }
1099                         } else {        /* rv 100 */
1100                                 /* rv100 might not need 64 pix alignment, who knows */
1101                                 /* offsets are, hmm, weird */
1102                                 tileoffset =
1103                                     ((pbox[i].y1 >> 4) * depthpixperline +
1104                                      pbox[i].x1) >> 6;
1105                                 nrtilesx =
1106                                     ((pbox[i].x2 & ~63) -
1107                                      (pbox[i].x1 & ~63)) >> 4;
1108                                 nrtilesy =
1109                                     (pbox[i].y2 >> 4) - (pbox[i].y1 >> 4);
1110                                 for (j = 0; j <= nrtilesy; j++) {
1111                                         BEGIN_RING(4);
1112                                         OUT_RING(CP_PACKET3
1113                                                  (RADEON_3D_CLEAR_ZMASK, 2));
1114                                         OUT_RING(tileoffset * 128);
1115                                         /* the number of tiles to clear */
1116                                         OUT_RING(nrtilesx + 4);
1117                                         /* clear mask : chooses the clearing pattern. */
1118                                         OUT_RING(clearmask);
1119                                         ADVANCE_RING();
1120                                         tileoffset += depthpixperline >> 6;
1121                                 }
1122                         }
1123                 }
1124
1125                 /* TODO don't always clear all hi-level z tiles */
1126                 if ((dev_priv->flags & RADEON_HAS_HIERZ)
1127                     && (dev_priv->microcode_version == UCODE_R200)
1128                     && (flags & RADEON_USE_HIERZ))
1129                         /* r100 and cards without hierarchical z-buffer have no high-level z-buffer */
1130                         /* FIXME : the mask supposedly contains low-res z values. So can't set
1131                            just to the max (0xff? or actually 0x3fff?), need to take z clear
1132                            value into account? */
1133                 {
1134                         BEGIN_RING(4);
1135                         OUT_RING(CP_PACKET3(RADEON_3D_CLEAR_HIZ, 2));
1136                         OUT_RING(0x0);  /* First tile */
1137                         OUT_RING(0x3cc0);
1138                         OUT_RING((0xff << 22) | (0xff << 6) | 0x003f003f);
1139                         ADVANCE_RING();
1140                 }
1141         }
1142
1143         /* We have to clear the depth and/or stencil buffers by
1144          * rendering a quad into just those buffers.  Thus, we have to
1145          * make sure the 3D engine is configured correctly.
1146          */
1147         else if ((dev_priv->microcode_version == UCODE_R200) &&
1148                 (flags & (RADEON_DEPTH | RADEON_STENCIL))) {
1149
1150                 int tempPP_CNTL;
1151                 int tempRE_CNTL;
1152                 int tempRB3D_CNTL;
1153                 int tempRB3D_ZSTENCILCNTL;
1154                 int tempRB3D_STENCILREFMASK;
1155                 int tempRB3D_PLANEMASK;
1156                 int tempSE_CNTL;
1157                 int tempSE_VTE_CNTL;
1158                 int tempSE_VTX_FMT_0;
1159                 int tempSE_VTX_FMT_1;
1160                 int tempSE_VAP_CNTL;
1161                 int tempRE_AUX_SCISSOR_CNTL;
1162
1163                 tempPP_CNTL = 0;
1164                 tempRE_CNTL = 0;
1165
1166                 tempRB3D_CNTL = depth_clear->rb3d_cntl;
1167
1168                 tempRB3D_ZSTENCILCNTL = depth_clear->rb3d_zstencilcntl;
1169                 tempRB3D_STENCILREFMASK = 0x0;
1170
1171                 tempSE_CNTL = depth_clear->se_cntl;
1172
1173                 /* Disable TCL */
1174
1175                 tempSE_VAP_CNTL = (     /* SE_VAP_CNTL__FORCE_W_TO_ONE_MASK |  */
1176                                           (0x9 <<
1177                                            SE_VAP_CNTL__VF_MAX_VTX_NUM__SHIFT));
1178
1179                 tempRB3D_PLANEMASK = 0x0;
1180
1181                 tempRE_AUX_SCISSOR_CNTL = 0x0;
1182
1183                 tempSE_VTE_CNTL =
1184                     SE_VTE_CNTL__VTX_XY_FMT_MASK | SE_VTE_CNTL__VTX_Z_FMT_MASK;
1185
1186                 /* Vertex format (X, Y, Z, W) */
1187                 tempSE_VTX_FMT_0 =
1188                     SE_VTX_FMT_0__VTX_Z0_PRESENT_MASK |
1189                     SE_VTX_FMT_0__VTX_W0_PRESENT_MASK;
1190                 tempSE_VTX_FMT_1 = 0x0;
1191
1192                 /*
1193                  * Depth buffer specific enables
1194                  */
1195                 if (flags & RADEON_DEPTH) {
1196                         /* Enable depth buffer */
1197                         tempRB3D_CNTL |= RADEON_Z_ENABLE;
1198                 } else {
1199                         /* Disable depth buffer */
1200                         tempRB3D_CNTL &= ~RADEON_Z_ENABLE;
1201                 }
1202
1203                 /*
1204                  * Stencil buffer specific enables
1205                  */
1206                 if (flags & RADEON_STENCIL) {
1207                         tempRB3D_CNTL |= RADEON_STENCIL_ENABLE;
1208                         tempRB3D_STENCILREFMASK = clear->depth_mask;
1209                 } else {
1210                         tempRB3D_CNTL &= ~RADEON_STENCIL_ENABLE;
1211                         tempRB3D_STENCILREFMASK = 0x00000000;
1212                 }
1213
1214                 if (flags & RADEON_USE_COMP_ZBUF) {
1215                         tempRB3D_ZSTENCILCNTL |= RADEON_Z_COMPRESSION_ENABLE |
1216                             RADEON_Z_DECOMPRESSION_ENABLE;
1217                 }
1218                 if (flags & RADEON_USE_HIERZ) {
1219                         tempRB3D_ZSTENCILCNTL |= RADEON_Z_HIERARCHY_ENABLE;
1220                 }
1221
1222                 BEGIN_RING(26);
1223                 RADEON_WAIT_UNTIL_2D_IDLE();
1224
1225                 OUT_RING_REG(RADEON_PP_CNTL, tempPP_CNTL);
1226                 OUT_RING_REG(R200_RE_CNTL, tempRE_CNTL);
1227                 OUT_RING_REG(RADEON_RB3D_CNTL, tempRB3D_CNTL);
1228                 OUT_RING_REG(RADEON_RB3D_ZSTENCILCNTL, tempRB3D_ZSTENCILCNTL);
1229                 OUT_RING_REG(RADEON_RB3D_STENCILREFMASK,
1230                              tempRB3D_STENCILREFMASK);
1231                 OUT_RING_REG(RADEON_RB3D_PLANEMASK, tempRB3D_PLANEMASK);
1232                 OUT_RING_REG(RADEON_SE_CNTL, tempSE_CNTL);
1233                 OUT_RING_REG(R200_SE_VTE_CNTL, tempSE_VTE_CNTL);
1234                 OUT_RING_REG(R200_SE_VTX_FMT_0, tempSE_VTX_FMT_0);
1235                 OUT_RING_REG(R200_SE_VTX_FMT_1, tempSE_VTX_FMT_1);
1236                 OUT_RING_REG(R200_SE_VAP_CNTL, tempSE_VAP_CNTL);
1237                 OUT_RING_REG(R200_RE_AUX_SCISSOR_CNTL, tempRE_AUX_SCISSOR_CNTL);
1238                 ADVANCE_RING();
1239
1240                 /* Make sure we restore the 3D state next time.
1241                  */
1242                 sarea_priv->ctx_owner = 0;
1243
1244                 for (i = 0; i < nbox; i++) {
1245
1246                         /* Funny that this should be required --
1247                          *  sets top-left?
1248                          */
1249                         radeon_emit_clip_rect(dev_priv, &sarea_priv->boxes[i]);
1250
1251                         BEGIN_RING(14);
1252                         OUT_RING(CP_PACKET3(R200_3D_DRAW_IMMD_2, 12));
1253                         OUT_RING((RADEON_PRIM_TYPE_RECT_LIST |
1254                                   RADEON_PRIM_WALK_RING |
1255                                   (3 << RADEON_NUM_VERTICES_SHIFT)));
1256                         OUT_RING(depth_boxes[i].ui[CLEAR_X1]);
1257                         OUT_RING(depth_boxes[i].ui[CLEAR_Y1]);
1258                         OUT_RING(depth_boxes[i].ui[CLEAR_DEPTH]);
1259                         OUT_RING(0x3f800000);
1260                         OUT_RING(depth_boxes[i].ui[CLEAR_X1]);
1261                         OUT_RING(depth_boxes[i].ui[CLEAR_Y2]);
1262                         OUT_RING(depth_boxes[i].ui[CLEAR_DEPTH]);
1263                         OUT_RING(0x3f800000);
1264                         OUT_RING(depth_boxes[i].ui[CLEAR_X2]);
1265                         OUT_RING(depth_boxes[i].ui[CLEAR_Y2]);
1266                         OUT_RING(depth_boxes[i].ui[CLEAR_DEPTH]);
1267                         OUT_RING(0x3f800000);
1268                         ADVANCE_RING();
1269                 }
1270         } else if ((flags & (RADEON_DEPTH | RADEON_STENCIL))) {
1271
1272                 int tempRB3D_ZSTENCILCNTL = depth_clear->rb3d_zstencilcntl;
1273
1274                 rb3d_cntl = depth_clear->rb3d_cntl;
1275
1276                 if (flags & RADEON_DEPTH) {
1277                         rb3d_cntl |= RADEON_Z_ENABLE;
1278                 } else {
1279                         rb3d_cntl &= ~RADEON_Z_ENABLE;
1280                 }
1281
1282                 if (flags & RADEON_STENCIL) {
1283                         rb3d_cntl |= RADEON_STENCIL_ENABLE;
1284                         rb3d_stencilrefmask = clear->depth_mask;        /* misnamed field */
1285                 } else {
1286                         rb3d_cntl &= ~RADEON_STENCIL_ENABLE;
1287                         rb3d_stencilrefmask = 0x00000000;
1288                 }
1289
1290                 if (flags & RADEON_USE_COMP_ZBUF) {
1291                         tempRB3D_ZSTENCILCNTL |= RADEON_Z_COMPRESSION_ENABLE |
1292                             RADEON_Z_DECOMPRESSION_ENABLE;
1293                 }
1294                 if (flags & RADEON_USE_HIERZ) {
1295                         tempRB3D_ZSTENCILCNTL |= RADEON_Z_HIERARCHY_ENABLE;
1296                 }
1297
1298                 BEGIN_RING(13);
1299                 RADEON_WAIT_UNTIL_2D_IDLE();
1300
1301                 OUT_RING(CP_PACKET0(RADEON_PP_CNTL, 1));
1302                 OUT_RING(0x00000000);
1303                 OUT_RING(rb3d_cntl);
1304
1305                 OUT_RING_REG(RADEON_RB3D_ZSTENCILCNTL, tempRB3D_ZSTENCILCNTL);
1306                 OUT_RING_REG(RADEON_RB3D_STENCILREFMASK, rb3d_stencilrefmask);
1307                 OUT_RING_REG(RADEON_RB3D_PLANEMASK, 0x00000000);
1308                 OUT_RING_REG(RADEON_SE_CNTL, depth_clear->se_cntl);
1309                 ADVANCE_RING();
1310
1311                 /* Make sure we restore the 3D state next time.
1312                  */
1313                 sarea_priv->ctx_owner = 0;
1314
1315                 for (i = 0; i < nbox; i++) {
1316
1317                         /* Funny that this should be required --
1318                          *  sets top-left?
1319                          */
1320                         radeon_emit_clip_rect(dev_priv, &sarea_priv->boxes[i]);
1321
1322                         BEGIN_RING(15);
1323
1324                         OUT_RING(CP_PACKET3(RADEON_3D_DRAW_IMMD, 13));
1325                         OUT_RING(RADEON_VTX_Z_PRESENT |
1326                                  RADEON_VTX_PKCOLOR_PRESENT);
1327                         OUT_RING((RADEON_PRIM_TYPE_RECT_LIST |
1328                                   RADEON_PRIM_WALK_RING |
1329                                   RADEON_MAOS_ENABLE |
1330                                   RADEON_VTX_FMT_RADEON_MODE |
1331                                   (3 << RADEON_NUM_VERTICES_SHIFT)));
1332
1333                         OUT_RING(depth_boxes[i].ui[CLEAR_X1]);
1334                         OUT_RING(depth_boxes[i].ui[CLEAR_Y1]);
1335                         OUT_RING(depth_boxes[i].ui[CLEAR_DEPTH]);
1336                         OUT_RING(0x0);
1337
1338                         OUT_RING(depth_boxes[i].ui[CLEAR_X1]);
1339                         OUT_RING(depth_boxes[i].ui[CLEAR_Y2]);
1340                         OUT_RING(depth_boxes[i].ui[CLEAR_DEPTH]);
1341                         OUT_RING(0x0);
1342
1343                         OUT_RING(depth_boxes[i].ui[CLEAR_X2]);
1344                         OUT_RING(depth_boxes[i].ui[CLEAR_Y2]);
1345                         OUT_RING(depth_boxes[i].ui[CLEAR_DEPTH]);
1346                         OUT_RING(0x0);
1347
1348                         ADVANCE_RING();
1349                 }
1350         }
1351
1352         /* Increment the clear counter.  The client-side 3D driver must
1353          * wait on this value before performing the clear ioctl.  We
1354          * need this because the card's so damned fast...
1355          */
1356         sarea_priv->last_clear++;
1357
1358         BEGIN_RING(4);
1359
1360         RADEON_CLEAR_AGE(sarea_priv->last_clear);
1361         RADEON_WAIT_UNTIL_IDLE();
1362
1363         ADVANCE_RING();
1364 }
1365
1366 static void radeon_cp_dispatch_swap(struct drm_device *dev, struct drm_master *master)
1367 {
1368         drm_radeon_private_t *dev_priv = dev->dev_private;
1369         struct drm_radeon_master_private *master_priv = master->driver_priv;
1370         drm_radeon_sarea_t *sarea_priv = master_priv->sarea_priv;
1371         int nbox = sarea_priv->nbox;
1372         struct drm_clip_rect *pbox = sarea_priv->boxes;
1373         int i;
1374         RING_LOCALS;
1375         DRM_DEBUG("\n");
1376
1377         /* Do some trivial performance monitoring...
1378          */
1379         if (dev_priv->do_boxes)
1380                 radeon_cp_performance_boxes(dev_priv, master_priv);
1381
1382         /* Wait for the 3D stream to idle before dispatching the bitblt.
1383          * This will prevent data corruption between the two streams.
1384          */
1385         BEGIN_RING(2);
1386
1387         RADEON_WAIT_UNTIL_3D_IDLE();
1388
1389         ADVANCE_RING();
1390
1391         for (i = 0; i < nbox; i++) {
1392                 int x = pbox[i].x1;
1393                 int y = pbox[i].y1;
1394                 int w = pbox[i].x2 - x;
1395                 int h = pbox[i].y2 - y;
1396
1397                 DRM_DEBUG("%d,%d-%d,%d\n", x, y, w, h);
1398
1399                 BEGIN_RING(9);
1400
1401                 OUT_RING(CP_PACKET0(RADEON_DP_GUI_MASTER_CNTL, 0));
1402                 OUT_RING(RADEON_GMC_SRC_PITCH_OFFSET_CNTL |
1403                          RADEON_GMC_DST_PITCH_OFFSET_CNTL |
1404                          RADEON_GMC_BRUSH_NONE |
1405                          (dev_priv->color_fmt << 8) |
1406                          RADEON_GMC_SRC_DATATYPE_COLOR |
1407                          RADEON_ROP3_S |
1408                          RADEON_DP_SRC_SOURCE_MEMORY |
1409                          RADEON_GMC_CLR_CMP_CNTL_DIS | RADEON_GMC_WR_MSK_DIS);
1410
1411                 /* Make this work even if front & back are flipped:
1412                  */
1413                 OUT_RING(CP_PACKET0(RADEON_SRC_PITCH_OFFSET, 1));
1414                 if (sarea_priv->pfCurrentPage == 0) {
1415                         OUT_RING(dev_priv->back_pitch_offset);
1416                         OUT_RING(dev_priv->front_pitch_offset);
1417                 } else {
1418                         OUT_RING(dev_priv->front_pitch_offset);
1419                         OUT_RING(dev_priv->back_pitch_offset);
1420                 }
1421
1422                 OUT_RING(CP_PACKET0(RADEON_SRC_X_Y, 2));
1423                 OUT_RING((x << 16) | y);
1424                 OUT_RING((x << 16) | y);
1425                 OUT_RING((w << 16) | h);
1426
1427                 ADVANCE_RING();
1428         }
1429
1430         /* Increment the frame counter.  The client-side 3D driver must
1431          * throttle the framerate by waiting for this value before
1432          * performing the swapbuffer ioctl.
1433          */
1434         sarea_priv->last_frame++;
1435
1436         BEGIN_RING(4);
1437
1438         RADEON_FRAME_AGE(sarea_priv->last_frame);
1439         RADEON_WAIT_UNTIL_2D_IDLE();
1440
1441         ADVANCE_RING();
1442 }
1443
1444 void radeon_cp_dispatch_flip(struct drm_device *dev, struct drm_master *master)
1445 {
1446         drm_radeon_private_t *dev_priv = dev->dev_private;
1447         struct drm_radeon_master_private *master_priv = master->driver_priv;
1448         struct drm_sarea *sarea = (struct drm_sarea *)master_priv->sarea->handle;
1449         int offset = (master_priv->sarea_priv->pfCurrentPage == 1)
1450             ? dev_priv->front_offset : dev_priv->back_offset;
1451         RING_LOCALS;
1452         DRM_DEBUG("pfCurrentPage=%d\n",
1453                   master_priv->sarea_priv->pfCurrentPage);
1454
1455         /* Do some trivial performance monitoring...
1456          */
1457         if (dev_priv->do_boxes) {
1458                 dev_priv->stats.boxes |= RADEON_BOX_FLIP;
1459                 radeon_cp_performance_boxes(dev_priv, master_priv);
1460         }
1461
1462         /* Update the frame offsets for both CRTCs
1463          */
1464         BEGIN_RING(6);
1465
1466         RADEON_WAIT_UNTIL_3D_IDLE();
1467         OUT_RING_REG(RADEON_CRTC_OFFSET,
1468                      ((sarea->frame.y * dev_priv->front_pitch +
1469                        sarea->frame.x * (dev_priv->color_fmt - 2)) & ~7)
1470                      + offset);
1471         OUT_RING_REG(RADEON_CRTC2_OFFSET, master_priv->sarea_priv->crtc2_base
1472                      + offset);
1473
1474         ADVANCE_RING();
1475
1476         /* Increment the frame counter.  The client-side 3D driver must
1477          * throttle the framerate by waiting for this value before
1478          * performing the swapbuffer ioctl.
1479          */
1480         master_priv->sarea_priv->last_frame++;
1481         master_priv->sarea_priv->pfCurrentPage =
1482                 1 - master_priv->sarea_priv->pfCurrentPage;
1483
1484         BEGIN_RING(2);
1485
1486         RADEON_FRAME_AGE(master_priv->sarea_priv->last_frame);
1487
1488         ADVANCE_RING();
1489 }
1490
1491 static int bad_prim_vertex_nr(int primitive, int nr)
1492 {
1493         switch (primitive & RADEON_PRIM_TYPE_MASK) {
1494         case RADEON_PRIM_TYPE_NONE:
1495         case RADEON_PRIM_TYPE_POINT:
1496                 return nr < 1;
1497         case RADEON_PRIM_TYPE_LINE:
1498                 return (nr & 1) || nr == 0;
1499         case RADEON_PRIM_TYPE_LINE_STRIP:
1500                 return nr < 2;
1501         case RADEON_PRIM_TYPE_TRI_LIST:
1502         case RADEON_PRIM_TYPE_3VRT_POINT_LIST:
1503         case RADEON_PRIM_TYPE_3VRT_LINE_LIST:
1504         case RADEON_PRIM_TYPE_RECT_LIST:
1505                 return nr % 3 || nr == 0;
1506         case RADEON_PRIM_TYPE_TRI_FAN:
1507         case RADEON_PRIM_TYPE_TRI_STRIP:
1508                 return nr < 3;
1509         default:
1510                 return 1;
1511         }
1512 }
1513
1514 typedef struct {
1515         unsigned int start;
1516         unsigned int finish;
1517         unsigned int prim;
1518         unsigned int numverts;
1519         unsigned int offset;
1520         unsigned int vc_format;
1521 } drm_radeon_tcl_prim_t;
1522
1523 static void radeon_cp_dispatch_vertex(struct drm_device * dev,
1524                                       struct drm_file *file_priv,
1525                                       struct drm_buf * buf,
1526                                       drm_radeon_tcl_prim_t * prim)
1527 {
1528         drm_radeon_private_t *dev_priv = dev->dev_private;
1529         struct drm_radeon_master_private *master_priv = file_priv->master->driver_priv;
1530         drm_radeon_sarea_t *sarea_priv = master_priv->sarea_priv;
1531         int offset = dev_priv->gart_buffers_offset + buf->offset + prim->start;
1532         int numverts = (int)prim->numverts;
1533         int nbox = sarea_priv->nbox;
1534         int i = 0;
1535         RING_LOCALS;
1536
1537         DRM_DEBUG("hwprim 0x%x vfmt 0x%x %d..%d %d verts\n",
1538                   prim->prim,
1539                   prim->vc_format, prim->start, prim->finish, prim->numverts);
1540
1541         if (bad_prim_vertex_nr(prim->prim, prim->numverts)) {
1542                 DRM_ERROR("bad prim %x numverts %d\n",
1543                           prim->prim, prim->numverts);
1544                 return;
1545         }
1546
1547         do {
1548                 /* Emit the next cliprect */
1549                 if (i < nbox) {
1550                         radeon_emit_clip_rect(dev_priv, &sarea_priv->boxes[i]);
1551                 }
1552
1553                 /* Emit the vertex buffer rendering commands */
1554                 BEGIN_RING(5);
1555
1556                 OUT_RING(CP_PACKET3(RADEON_3D_RNDR_GEN_INDX_PRIM, 3));
1557                 OUT_RING(offset);
1558                 OUT_RING(numverts);
1559                 OUT_RING(prim->vc_format);
1560                 OUT_RING(prim->prim | RADEON_PRIM_WALK_LIST |
1561                          RADEON_COLOR_ORDER_RGBA |
1562                          RADEON_VTX_FMT_RADEON_MODE |
1563                          (numverts << RADEON_NUM_VERTICES_SHIFT));
1564
1565                 ADVANCE_RING();
1566
1567                 i++;
1568         } while (i < nbox);
1569 }
1570
1571 void radeon_cp_discard_buffer(struct drm_device *dev, struct drm_master *master, struct drm_buf *buf)
1572 {
1573         drm_radeon_private_t *dev_priv = dev->dev_private;
1574         struct drm_radeon_master_private *master_priv = master->driver_priv;
1575         drm_radeon_buf_priv_t *buf_priv = buf->dev_private;
1576         RING_LOCALS;
1577
1578         buf_priv->age = ++master_priv->sarea_priv->last_dispatch;
1579
1580         /* Emit the vertex buffer age */
1581         if ((dev_priv->flags & RADEON_FAMILY_MASK) >= CHIP_R600) {
1582                 BEGIN_RING(3);
1583                 R600_DISPATCH_AGE(buf_priv->age);
1584                 ADVANCE_RING();
1585         } else {
1586                 BEGIN_RING(2);
1587                 RADEON_DISPATCH_AGE(buf_priv->age);
1588                 ADVANCE_RING();
1589         }
1590
1591         buf->pending = 1;
1592         buf->used = 0;
1593 }
1594
1595 static void radeon_cp_dispatch_indirect(struct drm_device * dev,
1596                                         struct drm_buf * buf, int start, int end)
1597 {
1598         drm_radeon_private_t *dev_priv = dev->dev_private;
1599         RING_LOCALS;
1600         DRM_DEBUG("buf=%d s=0x%x e=0x%x\n", buf->idx, start, end);
1601
1602         if (start != end) {
1603                 int offset = (dev_priv->gart_buffers_offset
1604                               + buf->offset + start);
1605                 int dwords = (end - start + 3) / sizeof(u32);
1606
1607                 /* Indirect buffer data must be an even number of
1608                  * dwords, so if we've been given an odd number we must
1609                  * pad the data with a Type-2 CP packet.
1610                  */
1611                 if (dwords & 1) {
1612                         u32 *data = (u32 *)
1613                             ((char *)dev->agp_buffer_map->handle
1614                              + buf->offset + start);
1615                         data[dwords++] = RADEON_CP_PACKET2;
1616                 }
1617
1618                 /* Fire off the indirect buffer */
1619                 BEGIN_RING(3);
1620
1621                 OUT_RING(CP_PACKET0(RADEON_CP_IB_BASE, 1));
1622                 OUT_RING(offset);
1623                 OUT_RING(dwords);
1624
1625                 ADVANCE_RING();
1626         }
1627 }
1628
1629 static void radeon_cp_dispatch_indices(struct drm_device *dev,
1630                                        struct drm_master *master,
1631                                        struct drm_buf * elt_buf,
1632                                        drm_radeon_tcl_prim_t * prim)
1633 {
1634         drm_radeon_private_t *dev_priv = dev->dev_private;
1635         struct drm_radeon_master_private *master_priv = master->driver_priv;
1636         drm_radeon_sarea_t *sarea_priv = master_priv->sarea_priv;
1637         int offset = dev_priv->gart_buffers_offset + prim->offset;
1638         u32 *data;
1639         int dwords;
1640         int i = 0;
1641         int start = prim->start + RADEON_INDEX_PRIM_OFFSET;
1642         int count = (prim->finish - start) / sizeof(u16);
1643         int nbox = sarea_priv->nbox;
1644
1645         DRM_DEBUG("hwprim 0x%x vfmt 0x%x %d..%d offset: %x nr %d\n",
1646                   prim->prim,
1647                   prim->vc_format,
1648                   prim->start, prim->finish, prim->offset, prim->numverts);
1649
1650         if (bad_prim_vertex_nr(prim->prim, count)) {
1651                 DRM_ERROR("bad prim %x count %d\n", prim->prim, count);
1652                 return;
1653         }
1654
1655         if (start >= prim->finish || (prim->start & 0x7)) {
1656                 DRM_ERROR("buffer prim %d\n", prim->prim);
1657                 return;
1658         }
1659
1660         dwords = (prim->finish - prim->start + 3) / sizeof(u32);
1661
1662         data = (u32 *) ((char *)dev->agp_buffer_map->handle +
1663                         elt_buf->offset + prim->start);
1664
1665         data[0] = CP_PACKET3(RADEON_3D_RNDR_GEN_INDX_PRIM, dwords - 2);
1666         data[1] = offset;
1667         data[2] = prim->numverts;
1668         data[3] = prim->vc_format;
1669         data[4] = (prim->prim |
1670                    RADEON_PRIM_WALK_IND |
1671                    RADEON_COLOR_ORDER_RGBA |
1672                    RADEON_VTX_FMT_RADEON_MODE |
1673                    (count << RADEON_NUM_VERTICES_SHIFT));
1674
1675         do {
1676                 if (i < nbox)
1677                         radeon_emit_clip_rect(dev_priv, &sarea_priv->boxes[i]);
1678
1679                 radeon_cp_dispatch_indirect(dev, elt_buf,
1680                                             prim->start, prim->finish);
1681
1682                 i++;
1683         } while (i < nbox);
1684
1685 }
1686
1687 #define RADEON_MAX_TEXTURE_SIZE RADEON_BUFFER_SIZE
1688
1689 static int radeon_cp_dispatch_texture(struct drm_device * dev,
1690                                       struct drm_file *file_priv,
1691                                       drm_radeon_texture_t * tex,
1692                                       drm_radeon_tex_image_t * image)
1693 {
1694         drm_radeon_private_t *dev_priv = dev->dev_private;
1695         struct drm_buf *buf;
1696         u32 format;
1697         u32 *buffer;
1698         const u8 __user *data;
1699         int size, dwords, tex_width, blit_width, spitch;
1700         u32 height;
1701         int i;
1702         u32 texpitch, microtile;
1703         u32 offset, byte_offset;
1704         RING_LOCALS;
1705
1706         if (radeon_check_and_fixup_offset(dev_priv, file_priv, &tex->offset)) {
1707                 DRM_ERROR("Invalid destination offset\n");
1708                 return -EINVAL;
1709         }
1710
1711         dev_priv->stats.boxes |= RADEON_BOX_TEXTURE_LOAD;
1712
1713         /* Flush the pixel cache.  This ensures no pixel data gets mixed
1714          * up with the texture data from the host data blit, otherwise
1715          * part of the texture image may be corrupted.
1716          */
1717         BEGIN_RING(4);
1718         RADEON_FLUSH_CACHE();
1719         RADEON_WAIT_UNTIL_IDLE();
1720         ADVANCE_RING();
1721
1722         /* The compiler won't optimize away a division by a variable,
1723          * even if the only legal values are powers of two.  Thus, we'll
1724          * use a shift instead.
1725          */
1726         switch (tex->format) {
1727         case RADEON_TXFORMAT_ARGB8888:
1728         case RADEON_TXFORMAT_RGBA8888:
1729                 format = RADEON_COLOR_FORMAT_ARGB8888;
1730                 tex_width = tex->width * 4;
1731                 blit_width = image->width * 4;
1732                 break;
1733         case RADEON_TXFORMAT_AI88:
1734         case RADEON_TXFORMAT_ARGB1555:
1735         case RADEON_TXFORMAT_RGB565:
1736         case RADEON_TXFORMAT_ARGB4444:
1737         case RADEON_TXFORMAT_VYUY422:
1738         case RADEON_TXFORMAT_YVYU422:
1739                 format = RADEON_COLOR_FORMAT_RGB565;
1740                 tex_width = tex->width * 2;
1741                 blit_width = image->width * 2;
1742                 break;
1743         case RADEON_TXFORMAT_I8:
1744         case RADEON_TXFORMAT_RGB332:
1745                 format = RADEON_COLOR_FORMAT_CI8;
1746                 tex_width = tex->width * 1;
1747                 blit_width = image->width * 1;
1748                 break;
1749         default:
1750                 DRM_ERROR("invalid texture format %d\n", tex->format);
1751                 return -EINVAL;
1752         }
1753         spitch = blit_width >> 6;
1754         if (spitch == 0 && image->height > 1)
1755                 return -EINVAL;
1756
1757         texpitch = tex->pitch;
1758         if ((texpitch << 22) & RADEON_DST_TILE_MICRO) {
1759                 microtile = 1;
1760                 if (tex_width < 64) {
1761                         texpitch &= ~(RADEON_DST_TILE_MICRO >> 22);
1762                         /* we got tiled coordinates, untile them */
1763                         image->x *= 2;
1764                 }
1765         } else
1766                 microtile = 0;
1767
1768         /* this might fail for zero-sized uploads - are those illegal? */
1769         if (!radeon_check_offset(dev_priv, tex->offset + image->height *
1770                                 blit_width - 1)) {
1771                 DRM_ERROR("Invalid final destination offset\n");
1772                 return -EINVAL;
1773         }
1774
1775         DRM_DEBUG("tex=%dx%d blit=%d\n", tex_width, tex->height, blit_width);
1776
1777         do {
1778                 DRM_DEBUG("tex: ofs=0x%x p=%d f=%d x=%hd y=%hd w=%hd h=%hd\n",
1779                           tex->offset >> 10, tex->pitch, tex->format,
1780                           image->x, image->y, image->width, image->height);
1781
1782                 /* Make a copy of some parameters in case we have to
1783                  * update them for a multi-pass texture blit.
1784                  */
1785                 height = image->height;
1786                 data = (const u8 __user *)image->data;
1787
1788                 size = height * blit_width;
1789
1790                 if (size > RADEON_MAX_TEXTURE_SIZE) {
1791                         height = RADEON_MAX_TEXTURE_SIZE / blit_width;
1792                         size = height * blit_width;
1793                 } else if (size < 4 && size > 0) {
1794                         size = 4;
1795                 } else if (size == 0) {
1796                         return 0;
1797                 }
1798
1799                 buf = radeon_freelist_get(dev);
1800                 if (0 && !buf) {
1801                         radeon_do_cp_idle(dev_priv);
1802                         buf = radeon_freelist_get(dev);
1803                 }
1804                 if (!buf) {
1805                         DRM_DEBUG("EAGAIN\n");
1806                         if (DRM_COPY_TO_USER(tex->image, image, sizeof(*image)))
1807                                 return -EFAULT;
1808                         return -EAGAIN;
1809                 }
1810
1811                 /* Dispatch the indirect buffer.
1812                  */
1813                 buffer =
1814                     (u32 *) ((char *)dev->agp_buffer_map->handle + buf->offset);
1815                 dwords = size / 4;
1816
1817 #define RADEON_COPY_MT(_buf, _data, _width) \
1818         do { \
1819                 if (DRM_COPY_FROM_USER(_buf, _data, (_width))) {\
1820                         DRM_ERROR("EFAULT on pad, %d bytes\n", (_width)); \
1821                         return -EFAULT; \
1822                 } \
1823         } while(0)
1824
1825                 if (microtile) {
1826                         /* texture micro tiling in use, minimum texture width is thus 16 bytes.
1827                            however, we cannot use blitter directly for texture width < 64 bytes,
1828                            since minimum tex pitch is 64 bytes and we need this to match
1829                            the texture width, otherwise the blitter will tile it wrong.
1830                            Thus, tiling manually in this case. Additionally, need to special
1831                            case tex height = 1, since our actual image will have height 2
1832                            and we need to ensure we don't read beyond the texture size
1833                            from user space. */
1834                         if (tex->height == 1) {
1835                                 if (tex_width >= 64 || tex_width <= 16) {
1836                                         RADEON_COPY_MT(buffer, data,
1837                                                 (int)(tex_width * sizeof(u32)));
1838                                 } else if (tex_width == 32) {
1839                                         RADEON_COPY_MT(buffer, data, 16);
1840                                         RADEON_COPY_MT(buffer + 8,
1841                                                        data + 16, 16);
1842                                 }
1843                         } else if (tex_width >= 64 || tex_width == 16) {
1844                                 RADEON_COPY_MT(buffer, data,
1845                                                (int)(dwords * sizeof(u32)));
1846                         } else if (tex_width < 16) {
1847                                 for (i = 0; i < tex->height; i++) {
1848                                         RADEON_COPY_MT(buffer, data, tex_width);
1849                                         buffer += 4;
1850                                         data += tex_width;
1851                                 }
1852                         } else if (tex_width == 32) {
1853                                 /* TODO: make sure this works when not fitting in one buffer
1854                                    (i.e. 32bytes x 2048...) */
1855                                 for (i = 0; i < tex->height; i += 2) {
1856                                         RADEON_COPY_MT(buffer, data, 16);
1857                                         data += 16;
1858                                         RADEON_COPY_MT(buffer + 8, data, 16);
1859                                         data += 16;
1860                                         RADEON_COPY_MT(buffer + 4, data, 16);
1861                                         data += 16;
1862                                         RADEON_COPY_MT(buffer + 12, data, 16);
1863                                         data += 16;
1864                                         buffer += 16;
1865                                 }
1866                         }
1867                 } else {
1868                         if (tex_width >= 32) {
1869                                 /* Texture image width is larger than the minimum, so we
1870                                  * can upload it directly.
1871                                  */
1872                                 RADEON_COPY_MT(buffer, data,
1873                                                (int)(dwords * sizeof(u32)));
1874                         } else {
1875                                 /* Texture image width is less than the minimum, so we
1876                                  * need to pad out each image scanline to the minimum
1877                                  * width.
1878                                  */
1879                                 for (i = 0; i < tex->height; i++) {
1880                                         RADEON_COPY_MT(buffer, data, tex_width);
1881                                         buffer += 8;
1882                                         data += tex_width;
1883                                 }
1884                         }
1885                 }
1886
1887 #undef RADEON_COPY_MT
1888                 byte_offset = (image->y & ~2047) * blit_width;
1889                 buf->file_priv = file_priv;
1890                 buf->used = size;
1891                 offset = dev_priv->gart_buffers_offset + buf->offset;
1892                 BEGIN_RING(9);
1893                 OUT_RING(CP_PACKET3(RADEON_CNTL_BITBLT_MULTI, 5));
1894                 OUT_RING(RADEON_GMC_SRC_PITCH_OFFSET_CNTL |
1895                          RADEON_GMC_DST_PITCH_OFFSET_CNTL |
1896                          RADEON_GMC_BRUSH_NONE |
1897                          (format << 8) |
1898                          RADEON_GMC_SRC_DATATYPE_COLOR |
1899                          RADEON_ROP3_S |
1900                          RADEON_DP_SRC_SOURCE_MEMORY |
1901                          RADEON_GMC_CLR_CMP_CNTL_DIS | RADEON_GMC_WR_MSK_DIS);
1902                 OUT_RING((spitch << 22) | (offset >> 10));
1903                 OUT_RING((texpitch << 22) | ((tex->offset >> 10) + (byte_offset >> 10)));
1904                 OUT_RING(0);
1905                 OUT_RING((image->x << 16) | (image->y % 2048));
1906                 OUT_RING((image->width << 16) | height);
1907                 RADEON_WAIT_UNTIL_2D_IDLE();
1908                 ADVANCE_RING();
1909                 COMMIT_RING();
1910
1911                 radeon_cp_discard_buffer(dev, file_priv->master, buf);
1912
1913                 /* Update the input parameters for next time */
1914                 image->y += height;
1915                 image->height -= height;
1916                 image->data = (const u8 __user *)image->data + size;
1917         } while (image->height > 0);
1918
1919         /* Flush the pixel cache after the blit completes.  This ensures
1920          * the texture data is written out to memory before rendering
1921          * continues.
1922          */
1923         BEGIN_RING(4);
1924         RADEON_FLUSH_CACHE();
1925         RADEON_WAIT_UNTIL_2D_IDLE();
1926         ADVANCE_RING();
1927         COMMIT_RING();
1928
1929         return 0;
1930 }
1931
1932 static void radeon_cp_dispatch_stipple(struct drm_device * dev, u32 * stipple)
1933 {
1934         drm_radeon_private_t *dev_priv = dev->dev_private;
1935         int i;
1936         RING_LOCALS;
1937         DRM_DEBUG("\n");
1938
1939         BEGIN_RING(35);
1940
1941         OUT_RING(CP_PACKET0(RADEON_RE_STIPPLE_ADDR, 0));
1942         OUT_RING(0x00000000);
1943
1944         OUT_RING(CP_PACKET0_TABLE(RADEON_RE_STIPPLE_DATA, 31));
1945         for (i = 0; i < 32; i++) {
1946                 OUT_RING(stipple[i]);
1947         }
1948
1949         ADVANCE_RING();
1950 }
1951
1952 static void radeon_apply_surface_regs(int surf_index,
1953                                       drm_radeon_private_t *dev_priv)
1954 {
1955         if (!dev_priv->mmio)
1956                 return;
1957
1958         radeon_do_cp_idle(dev_priv);
1959
1960         RADEON_WRITE(RADEON_SURFACE0_INFO + 16 * surf_index,
1961                      dev_priv->surfaces[surf_index].flags);
1962         RADEON_WRITE(RADEON_SURFACE0_LOWER_BOUND + 16 * surf_index,
1963                      dev_priv->surfaces[surf_index].lower);
1964         RADEON_WRITE(RADEON_SURFACE0_UPPER_BOUND + 16 * surf_index,
1965                      dev_priv->surfaces[surf_index].upper);
1966 }
1967
1968 /* Allocates a virtual surface
1969  * doesn't always allocate a real surface, will stretch an existing
1970  * surface when possible.
1971  *
1972  * Note that refcount can be at most 2, since during a free refcount=3
1973  * might mean we have to allocate a new surface which might not always
1974  * be available.
1975  * For example : we allocate three contiguous surfaces ABC. If B is
1976  * freed, we suddenly need two surfaces to store A and C, which might
1977  * not always be available.
1978  */
1979 static int alloc_surface(drm_radeon_surface_alloc_t *new,
1980                          drm_radeon_private_t *dev_priv,
1981                          struct drm_file *file_priv)
1982 {
1983         struct radeon_virt_surface *s;
1984         int i;
1985         int virt_surface_index;
1986         uint32_t new_upper, new_lower;
1987
1988         new_lower = new->address;
1989         new_upper = new_lower + new->size - 1;
1990
1991         /* sanity check */
1992         if ((new_lower >= new_upper) || (new->flags == 0) || (new->size == 0) ||
1993             ((new_upper & RADEON_SURF_ADDRESS_FIXED_MASK) !=
1994              RADEON_SURF_ADDRESS_FIXED_MASK)
1995             || ((new_lower & RADEON_SURF_ADDRESS_FIXED_MASK) != 0))
1996                 return -1;
1997
1998         /* make sure there is no overlap with existing surfaces */
1999         for (i = 0; i < RADEON_MAX_SURFACES; i++) {
2000                 if ((dev_priv->surfaces[i].refcount != 0) &&
2001                     (((new_lower >= dev_priv->surfaces[i].lower) &&
2002                       (new_lower < dev_priv->surfaces[i].upper)) ||
2003                      ((new_lower < dev_priv->surfaces[i].lower) &&
2004                       (new_upper > dev_priv->surfaces[i].lower)))) {
2005                         return -1;
2006                 }
2007         }
2008
2009         /* find a virtual surface */
2010         for (i = 0; i < 2 * RADEON_MAX_SURFACES; i++)
2011                 if (dev_priv->virt_surfaces[i].file_priv == NULL)
2012                         break;
2013         if (i == 2 * RADEON_MAX_SURFACES) {
2014                 return -1;
2015         }
2016         virt_surface_index = i;
2017
2018         /* try to reuse an existing surface */
2019         for (i = 0; i < RADEON_MAX_SURFACES; i++) {
2020                 /* extend before */
2021                 if ((dev_priv->surfaces[i].refcount == 1) &&
2022                     (new->flags == dev_priv->surfaces[i].flags) &&
2023                     (new_upper + 1 == dev_priv->surfaces[i].lower)) {
2024                         s = &(dev_priv->virt_surfaces[virt_surface_index]);
2025                         s->surface_index = i;
2026                         s->lower = new_lower;
2027                         s->upper = new_upper;
2028                         s->flags = new->flags;
2029                         s->file_priv = file_priv;
2030                         dev_priv->surfaces[i].refcount++;
2031                         dev_priv->surfaces[i].lower = s->lower;
2032                         radeon_apply_surface_regs(s->surface_index, dev_priv);
2033                         return virt_surface_index;
2034                 }
2035
2036                 /* extend after */
2037                 if ((dev_priv->surfaces[i].refcount == 1) &&
2038                     (new->flags == dev_priv->surfaces[i].flags) &&
2039                     (new_lower == dev_priv->surfaces[i].upper + 1)) {
2040                         s = &(dev_priv->virt_surfaces[virt_surface_index]);
2041                         s->surface_index = i;
2042                         s->lower = new_lower;
2043                         s->upper = new_upper;
2044                         s->flags = new->flags;
2045                         s->file_priv = file_priv;
2046                         dev_priv->surfaces[i].refcount++;
2047                         dev_priv->surfaces[i].upper = s->upper;
2048                         radeon_apply_surface_regs(s->surface_index, dev_priv);
2049                         return virt_surface_index;
2050                 }
2051         }
2052
2053         /* okay, we need a new one */
2054         for (i = 0; i < RADEON_MAX_SURFACES; i++) {
2055                 if (dev_priv->surfaces[i].refcount == 0) {
2056                         s = &(dev_priv->virt_surfaces[virt_surface_index]);
2057                         s->surface_index = i;
2058                         s->lower = new_lower;
2059                         s->upper = new_upper;
2060                         s->flags = new->flags;
2061                         s->file_priv = file_priv;
2062                         dev_priv->surfaces[i].refcount = 1;
2063                         dev_priv->surfaces[i].lower = s->lower;
2064                         dev_priv->surfaces[i].upper = s->upper;
2065                         dev_priv->surfaces[i].flags = s->flags;
2066                         radeon_apply_surface_regs(s->surface_index, dev_priv);
2067                         return virt_surface_index;
2068                 }
2069         }
2070
2071         /* we didn't find anything */
2072         return -1;
2073 }
2074
2075 static int free_surface(struct drm_file *file_priv,
2076                         drm_radeon_private_t * dev_priv,
2077                         int lower)
2078 {
2079         struct radeon_virt_surface *s;
2080         int i;
2081         /* find the virtual surface */
2082         for (i = 0; i < 2 * RADEON_MAX_SURFACES; i++) {
2083                 s = &(dev_priv->virt_surfaces[i]);
2084                 if (s->file_priv) {
2085                         if ((lower == s->lower) && (file_priv == s->file_priv))
2086                         {
2087                                 if (dev_priv->surfaces[s->surface_index].
2088                                     lower == s->lower)
2089                                         dev_priv->surfaces[s->surface_index].
2090                                             lower = s->upper;
2091
2092                                 if (dev_priv->surfaces[s->surface_index].
2093                                     upper == s->upper)
2094                                         dev_priv->surfaces[s->surface_index].
2095                                             upper = s->lower;
2096
2097                                 dev_priv->surfaces[s->surface_index].refcount--;
2098                                 if (dev_priv->surfaces[s->surface_index].
2099                                     refcount == 0)
2100                                         dev_priv->surfaces[s->surface_index].
2101                                             flags = 0;
2102                                 s->file_priv = NULL;
2103                                 radeon_apply_surface_regs(s->surface_index,
2104                                                           dev_priv);
2105                                 return 0;
2106                         }
2107                 }
2108         }
2109         return 1;
2110 }
2111
2112 static void radeon_surfaces_release(struct drm_file *file_priv,
2113                                     drm_radeon_private_t * dev_priv)
2114 {
2115         int i;
2116         for (i = 0; i < 2 * RADEON_MAX_SURFACES; i++) {
2117                 if (dev_priv->virt_surfaces[i].file_priv == file_priv)
2118                         free_surface(file_priv, dev_priv,
2119                                      dev_priv->virt_surfaces[i].lower);
2120         }
2121 }
2122
2123 /* ================================================================
2124  * IOCTL functions
2125  */
2126 static int radeon_surface_alloc(struct drm_device *dev, void *data, struct drm_file *file_priv)
2127 {
2128         drm_radeon_private_t *dev_priv = dev->dev_private;
2129         drm_radeon_surface_alloc_t *alloc = data;
2130
2131         if (alloc_surface(alloc, dev_priv, file_priv) == -1)
2132                 return -EINVAL;
2133         else
2134                 return 0;
2135 }
2136
2137 static int radeon_surface_free(struct drm_device *dev, void *data, struct drm_file *file_priv)
2138 {
2139         drm_radeon_private_t *dev_priv = dev->dev_private;
2140         drm_radeon_surface_free_t *memfree = data;
2141
2142         if (free_surface(file_priv, dev_priv, memfree->address))
2143                 return -EINVAL;
2144         else
2145                 return 0;
2146 }
2147
2148 static int radeon_cp_clear(struct drm_device *dev, void *data, struct drm_file *file_priv)
2149 {
2150         drm_radeon_private_t *dev_priv = dev->dev_private;
2151         struct drm_radeon_master_private *master_priv = file_priv->master->driver_priv;
2152         drm_radeon_sarea_t *sarea_priv = master_priv->sarea_priv;
2153         drm_radeon_clear_t *clear = data;
2154         drm_radeon_clear_rect_t depth_boxes[RADEON_NR_SAREA_CLIPRECTS];
2155         DRM_DEBUG("\n");
2156
2157         LOCK_TEST_WITH_RETURN(dev, file_priv);
2158
2159         RING_SPACE_TEST_WITH_RETURN(dev_priv);
2160
2161         if (sarea_priv->nbox > RADEON_NR_SAREA_CLIPRECTS)
2162                 sarea_priv->nbox = RADEON_NR_SAREA_CLIPRECTS;
2163
2164         if (DRM_COPY_FROM_USER(&depth_boxes, clear->depth_boxes,
2165                                sarea_priv->nbox * sizeof(depth_boxes[0])))
2166                 return -EFAULT;
2167
2168         radeon_cp_dispatch_clear(dev, file_priv->master, clear, depth_boxes);
2169
2170         COMMIT_RING();
2171         return 0;
2172 }
2173
2174 /* Not sure why this isn't set all the time:
2175  */
2176 static int radeon_do_init_pageflip(struct drm_device *dev, struct drm_master *master)
2177 {
2178         drm_radeon_private_t *dev_priv = dev->dev_private;
2179         struct drm_radeon_master_private *master_priv = master->driver_priv;
2180         RING_LOCALS;
2181
2182         DRM_DEBUG("\n");
2183
2184         BEGIN_RING(6);
2185         RADEON_WAIT_UNTIL_3D_IDLE();
2186         OUT_RING(CP_PACKET0(RADEON_CRTC_OFFSET_CNTL, 0));
2187         OUT_RING(RADEON_READ(RADEON_CRTC_OFFSET_CNTL) |
2188                  RADEON_CRTC_OFFSET_FLIP_CNTL);
2189         OUT_RING(CP_PACKET0(RADEON_CRTC2_OFFSET_CNTL, 0));
2190         OUT_RING(RADEON_READ(RADEON_CRTC2_OFFSET_CNTL) |
2191                  RADEON_CRTC_OFFSET_FLIP_CNTL);
2192         ADVANCE_RING();
2193
2194         dev_priv->page_flipping = 1;
2195
2196         if (master_priv->sarea_priv->pfCurrentPage != 1)
2197                 master_priv->sarea_priv->pfCurrentPage = 0;
2198
2199         return 0;
2200 }
2201
2202 /* Swapping and flipping are different operations, need different ioctls.
2203  * They can & should be intermixed to support multiple 3d windows.
2204  */
2205 static int radeon_cp_flip(struct drm_device *dev, void *data, struct drm_file *file_priv)
2206 {
2207         drm_radeon_private_t *dev_priv = dev->dev_private;
2208         DRM_DEBUG("\n");
2209
2210         LOCK_TEST_WITH_RETURN(dev, file_priv);
2211
2212         RING_SPACE_TEST_WITH_RETURN(dev_priv);
2213
2214         if (!dev_priv->page_flipping)
2215                 radeon_do_init_pageflip(dev, file_priv->master);
2216
2217         radeon_cp_dispatch_flip(dev, file_priv->master);
2218
2219         COMMIT_RING();
2220         return 0;
2221 }
2222
2223 static int radeon_cp_swap(struct drm_device *dev, void *data, struct drm_file *file_priv)
2224 {
2225         drm_radeon_private_t *dev_priv = dev->dev_private;
2226         struct drm_radeon_master_private *master_priv = file_priv->master->driver_priv;
2227         drm_radeon_sarea_t *sarea_priv = master_priv->sarea_priv;
2228
2229         DRM_DEBUG("\n");
2230
2231         LOCK_TEST_WITH_RETURN(dev, file_priv);
2232
2233         RING_SPACE_TEST_WITH_RETURN(dev_priv);
2234
2235         if (sarea_priv->nbox > RADEON_NR_SAREA_CLIPRECTS)
2236                 sarea_priv->nbox = RADEON_NR_SAREA_CLIPRECTS;
2237
2238         if ((dev_priv->flags & RADEON_FAMILY_MASK) >= CHIP_R600)
2239                 r600_cp_dispatch_swap(dev, file_priv);
2240         else
2241                 radeon_cp_dispatch_swap(dev, file_priv->master);
2242         sarea_priv->ctx_owner = 0;
2243
2244         COMMIT_RING();
2245         return 0;
2246 }
2247
2248 static int radeon_cp_vertex(struct drm_device *dev, void *data, struct drm_file *file_priv)
2249 {
2250         drm_radeon_private_t *dev_priv = dev->dev_private;
2251         struct drm_radeon_master_private *master_priv = file_priv->master->driver_priv;
2252         drm_radeon_sarea_t *sarea_priv;
2253         struct drm_device_dma *dma = dev->dma;
2254         struct drm_buf *buf;
2255         drm_radeon_vertex_t *vertex = data;
2256         drm_radeon_tcl_prim_t prim;
2257
2258         LOCK_TEST_WITH_RETURN(dev, file_priv);
2259
2260         sarea_priv = master_priv->sarea_priv;
2261
2262         DRM_DEBUG("pid=%d index=%d count=%d discard=%d\n",
2263                   DRM_CURRENTPID, vertex->idx, vertex->count, vertex->discard);
2264
2265         if (vertex->idx < 0 || vertex->idx >= dma->buf_count) {
2266                 DRM_ERROR("buffer index %d (of %d max)\n",
2267                           vertex->idx, dma->buf_count - 1);
2268                 return -EINVAL;
2269         }
2270         if (vertex->prim < 0 || vertex->prim > RADEON_PRIM_TYPE_3VRT_LINE_LIST) {
2271                 DRM_ERROR("buffer prim %d\n", vertex->prim);
2272                 return -EINVAL;
2273         }
2274
2275         RING_SPACE_TEST_WITH_RETURN(dev_priv);
2276         VB_AGE_TEST_WITH_RETURN(dev_priv);
2277
2278         buf = dma->buflist[vertex->idx];
2279
2280         if (buf->file_priv != file_priv) {
2281                 DRM_ERROR("process %d using buffer owned by %p\n",
2282                           DRM_CURRENTPID, buf->file_priv);
2283                 return -EINVAL;
2284         }
2285         if (buf->pending) {
2286                 DRM_ERROR("sending pending buffer %d\n", vertex->idx);
2287                 return -EINVAL;
2288         }
2289
2290         /* Build up a prim_t record:
2291          */
2292         if (vertex->count) {
2293                 buf->used = vertex->count;      /* not used? */
2294
2295                 if (sarea_priv->dirty & ~RADEON_UPLOAD_CLIPRECTS) {
2296                         if (radeon_emit_state(dev_priv, file_priv,
2297                                               &sarea_priv->context_state,
2298                                               sarea_priv->tex_state,
2299                                               sarea_priv->dirty)) {
2300                                 DRM_ERROR("radeon_emit_state failed\n");
2301                                 return -EINVAL;
2302                         }
2303
2304                         sarea_priv->dirty &= ~(RADEON_UPLOAD_TEX0IMAGES |
2305                                                RADEON_UPLOAD_TEX1IMAGES |
2306                                                RADEON_UPLOAD_TEX2IMAGES |
2307                                                RADEON_REQUIRE_QUIESCENCE);
2308                 }
2309
2310                 prim.start = 0;
2311                 prim.finish = vertex->count;    /* unused */
2312                 prim.prim = vertex->prim;
2313                 prim.numverts = vertex->count;
2314                 prim.vc_format = sarea_priv->vc_format;
2315
2316                 radeon_cp_dispatch_vertex(dev, file_priv, buf, &prim);
2317         }
2318
2319         if (vertex->discard) {
2320                 radeon_cp_discard_buffer(dev, file_priv->master, buf);
2321         }
2322
2323         COMMIT_RING();
2324         return 0;
2325 }
2326
2327 static int radeon_cp_indices(struct drm_device *dev, void *data, struct drm_file *file_priv)
2328 {
2329         drm_radeon_private_t *dev_priv = dev->dev_private;
2330         struct drm_radeon_master_private *master_priv = file_priv->master->driver_priv;
2331         drm_radeon_sarea_t *sarea_priv;
2332         struct drm_device_dma *dma = dev->dma;
2333         struct drm_buf *buf;
2334         drm_radeon_indices_t *elts = data;
2335         drm_radeon_tcl_prim_t prim;
2336         int count;
2337
2338         LOCK_TEST_WITH_RETURN(dev, file_priv);
2339
2340         sarea_priv = master_priv->sarea_priv;
2341
2342         DRM_DEBUG("pid=%d index=%d start=%d end=%d discard=%d\n",
2343                   DRM_CURRENTPID, elts->idx, elts->start, elts->end,
2344                   elts->discard);
2345
2346         if (elts->idx < 0 || elts->idx >= dma->buf_count) {
2347                 DRM_ERROR("buffer index %d (of %d max)\n",
2348                           elts->idx, dma->buf_count - 1);
2349                 return -EINVAL;
2350         }
2351         if (elts->prim < 0 || elts->prim > RADEON_PRIM_TYPE_3VRT_LINE_LIST) {
2352                 DRM_ERROR("buffer prim %d\n", elts->prim);
2353                 return -EINVAL;
2354         }
2355
2356         RING_SPACE_TEST_WITH_RETURN(dev_priv);
2357         VB_AGE_TEST_WITH_RETURN(dev_priv);
2358
2359         buf = dma->buflist[elts->idx];
2360
2361         if (buf->file_priv != file_priv) {
2362                 DRM_ERROR("process %d using buffer owned by %p\n",
2363                           DRM_CURRENTPID, buf->file_priv);
2364                 return -EINVAL;
2365         }
2366         if (buf->pending) {
2367                 DRM_ERROR("sending pending buffer %d\n", elts->idx);
2368                 return -EINVAL;
2369         }
2370
2371         count = (elts->end - elts->start) / sizeof(u16);
2372         elts->start -= RADEON_INDEX_PRIM_OFFSET;
2373
2374         if (elts->start & 0x7) {
2375                 DRM_ERROR("misaligned buffer 0x%x\n", elts->start);
2376                 return -EINVAL;
2377         }
2378         if (elts->start < buf->used) {
2379                 DRM_ERROR("no header 0x%x - 0x%x\n", elts->start, buf->used);
2380                 return -EINVAL;
2381         }
2382
2383         buf->used = elts->end;
2384
2385         if (sarea_priv->dirty & ~RADEON_UPLOAD_CLIPRECTS) {
2386                 if (radeon_emit_state(dev_priv, file_priv,
2387                                       &sarea_priv->context_state,
2388                                       sarea_priv->tex_state,
2389                                       sarea_priv->dirty)) {
2390                         DRM_ERROR("radeon_emit_state failed\n");
2391                         return -EINVAL;
2392                 }
2393
2394                 sarea_priv->dirty &= ~(RADEON_UPLOAD_TEX0IMAGES |
2395                                        RADEON_UPLOAD_TEX1IMAGES |
2396                                        RADEON_UPLOAD_TEX2IMAGES |
2397                                        RADEON_REQUIRE_QUIESCENCE);
2398         }
2399
2400         /* Build up a prim_t record:
2401          */
2402         prim.start = elts->start;
2403         prim.finish = elts->end;
2404         prim.prim = elts->prim;
2405         prim.offset = 0;        /* offset from start of dma buffers */
2406         prim.numverts = RADEON_MAX_VB_VERTS;    /* duh */
2407         prim.vc_format = sarea_priv->vc_format;
2408
2409         radeon_cp_dispatch_indices(dev, file_priv->master, buf, &prim);
2410         if (elts->discard) {
2411                 radeon_cp_discard_buffer(dev, file_priv->master, buf);
2412         }
2413
2414         COMMIT_RING();
2415         return 0;
2416 }
2417
2418 static int radeon_cp_texture(struct drm_device *dev, void *data, struct drm_file *file_priv)
2419 {
2420         drm_radeon_private_t *dev_priv = dev->dev_private;
2421         drm_radeon_texture_t *tex = data;
2422         drm_radeon_tex_image_t image;
2423         int ret;
2424
2425         LOCK_TEST_WITH_RETURN(dev, file_priv);
2426
2427         if (tex->image == NULL) {
2428                 DRM_ERROR("null texture image!\n");
2429                 return -EINVAL;
2430         }
2431
2432         if (DRM_COPY_FROM_USER(&image,
2433                                (drm_radeon_tex_image_t __user *) tex->image,
2434                                sizeof(image)))
2435                 return -EFAULT;
2436
2437         RING_SPACE_TEST_WITH_RETURN(dev_priv);
2438         VB_AGE_TEST_WITH_RETURN(dev_priv);
2439
2440         if ((dev_priv->flags & RADEON_FAMILY_MASK) >= CHIP_R600)
2441                 ret = r600_cp_dispatch_texture(dev, file_priv, tex, &image);
2442         else
2443                 ret = radeon_cp_dispatch_texture(dev, file_priv, tex, &image);
2444
2445         return ret;
2446 }
2447
2448 static int radeon_cp_stipple(struct drm_device *dev, void *data, struct drm_file *file_priv)
2449 {
2450         drm_radeon_private_t *dev_priv = dev->dev_private;
2451         drm_radeon_stipple_t *stipple = data;
2452         u32 mask[32];
2453
2454         LOCK_TEST_WITH_RETURN(dev, file_priv);
2455
2456         if (DRM_COPY_FROM_USER(&mask, stipple->mask, 32 * sizeof(u32)))
2457                 return -EFAULT;
2458
2459         RING_SPACE_TEST_WITH_RETURN(dev_priv);
2460
2461         radeon_cp_dispatch_stipple(dev, mask);
2462
2463         COMMIT_RING();
2464         return 0;
2465 }
2466
2467 static int radeon_cp_indirect(struct drm_device *dev, void *data, struct drm_file *file_priv)
2468 {
2469         drm_radeon_private_t *dev_priv = dev->dev_private;
2470         struct drm_device_dma *dma = dev->dma;
2471         struct drm_buf *buf;
2472         drm_radeon_indirect_t *indirect = data;
2473         RING_LOCALS;
2474
2475         LOCK_TEST_WITH_RETURN(dev, file_priv);
2476
2477         DRM_DEBUG("idx=%d s=%d e=%d d=%d\n",
2478                   indirect->idx, indirect->start, indirect->end,
2479                   indirect->discard);
2480
2481         if (indirect->idx < 0 || indirect->idx >= dma->buf_count) {
2482                 DRM_ERROR("buffer index %d (of %d max)\n",
2483                           indirect->idx, dma->buf_count - 1);
2484                 return -EINVAL;
2485         }
2486
2487         buf = dma->buflist[indirect->idx];
2488
2489         if (buf->file_priv != file_priv) {
2490                 DRM_ERROR("process %d using buffer owned by %p\n",
2491                           DRM_CURRENTPID, buf->file_priv);
2492                 return -EINVAL;
2493         }
2494         if (buf->pending) {
2495                 DRM_ERROR("sending pending buffer %d\n", indirect->idx);
2496                 return -EINVAL;
2497         }
2498
2499         if (indirect->start < buf->used) {
2500                 DRM_ERROR("reusing indirect: start=0x%x actual=0x%x\n",
2501                           indirect->start, buf->used);
2502                 return -EINVAL;
2503         }
2504
2505         RING_SPACE_TEST_WITH_RETURN(dev_priv);
2506         VB_AGE_TEST_WITH_RETURN(dev_priv);
2507
2508         buf->used = indirect->end;
2509
2510         /* Dispatch the indirect buffer full of commands from the
2511          * X server.  This is insecure and is thus only available to
2512          * privileged clients.
2513          */
2514         if ((dev_priv->flags & RADEON_FAMILY_MASK) >= CHIP_R600)
2515                 r600_cp_dispatch_indirect(dev, buf, indirect->start, indirect->end);
2516         else {
2517                 /* Wait for the 3D stream to idle before the indirect buffer
2518                  * containing 2D acceleration commands is processed.
2519                  */
2520                 BEGIN_RING(2);
2521                 RADEON_WAIT_UNTIL_3D_IDLE();
2522                 ADVANCE_RING();
2523                 radeon_cp_dispatch_indirect(dev, buf, indirect->start, indirect->end);
2524         }
2525
2526         if (indirect->discard) {
2527                 radeon_cp_discard_buffer(dev, file_priv->master, buf);
2528         }
2529
2530         COMMIT_RING();
2531         return 0;
2532 }
2533
2534 static int radeon_cp_vertex2(struct drm_device *dev, void *data, struct drm_file *file_priv)
2535 {
2536         drm_radeon_private_t *dev_priv = dev->dev_private;
2537         struct drm_radeon_master_private *master_priv = file_priv->master->driver_priv;
2538         drm_radeon_sarea_t *sarea_priv;
2539         struct drm_device_dma *dma = dev->dma;
2540         struct drm_buf *buf;
2541         drm_radeon_vertex2_t *vertex = data;
2542         int i;
2543         unsigned char laststate;
2544
2545         LOCK_TEST_WITH_RETURN(dev, file_priv);
2546
2547         sarea_priv = master_priv->sarea_priv;
2548
2549         DRM_DEBUG("pid=%d index=%d discard=%d\n",
2550                   DRM_CURRENTPID, vertex->idx, vertex->discard);
2551
2552         if (vertex->idx < 0 || vertex->idx >= dma->buf_count) {
2553                 DRM_ERROR("buffer index %d (of %d max)\n",
2554                           vertex->idx, dma->buf_count - 1);
2555                 return -EINVAL;
2556         }
2557
2558         RING_SPACE_TEST_WITH_RETURN(dev_priv);
2559         VB_AGE_TEST_WITH_RETURN(dev_priv);
2560
2561         buf = dma->buflist[vertex->idx];
2562
2563         if (buf->file_priv != file_priv) {
2564                 DRM_ERROR("process %d using buffer owned by %p\n",
2565                           DRM_CURRENTPID, buf->file_priv);
2566                 return -EINVAL;
2567         }
2568
2569         if (buf->pending) {
2570                 DRM_ERROR("sending pending buffer %d\n", vertex->idx);
2571                 return -EINVAL;
2572         }
2573
2574         if (sarea_priv->nbox > RADEON_NR_SAREA_CLIPRECTS)
2575                 return -EINVAL;
2576
2577         for (laststate = 0xff, i = 0; i < vertex->nr_prims; i++) {
2578                 drm_radeon_prim_t prim;
2579                 drm_radeon_tcl_prim_t tclprim;
2580
2581                 if (DRM_COPY_FROM_USER(&prim, &vertex->prim[i], sizeof(prim)))
2582                         return -EFAULT;
2583
2584                 if (prim.stateidx != laststate) {
2585                         drm_radeon_state_t state;
2586
2587                         if (DRM_COPY_FROM_USER(&state,
2588                                                &vertex->state[prim.stateidx],
2589                                                sizeof(state)))
2590                                 return -EFAULT;
2591
2592                         if (radeon_emit_state2(dev_priv, file_priv, &state)) {
2593                                 DRM_ERROR("radeon_emit_state2 failed\n");
2594                                 return -EINVAL;
2595                         }
2596
2597                         laststate = prim.stateidx;
2598                 }
2599
2600                 tclprim.start = prim.start;
2601                 tclprim.finish = prim.finish;
2602                 tclprim.prim = prim.prim;
2603                 tclprim.vc_format = prim.vc_format;
2604
2605                 if (prim.prim & RADEON_PRIM_WALK_IND) {
2606                         tclprim.offset = prim.numverts * 64;
2607                         tclprim.numverts = RADEON_MAX_VB_VERTS; /* duh */
2608
2609                         radeon_cp_dispatch_indices(dev, file_priv->master, buf, &tclprim);
2610                 } else {
2611                         tclprim.numverts = prim.numverts;
2612                         tclprim.offset = 0;     /* not used */
2613
2614                         radeon_cp_dispatch_vertex(dev, file_priv, buf, &tclprim);
2615                 }
2616
2617                 if (sarea_priv->nbox == 1)
2618                         sarea_priv->nbox = 0;
2619         }
2620
2621         if (vertex->discard) {
2622                 radeon_cp_discard_buffer(dev, file_priv->master, buf);
2623         }
2624
2625         COMMIT_RING();
2626         return 0;
2627 }
2628
2629 static int radeon_emit_packets(drm_radeon_private_t * dev_priv,
2630                                struct drm_file *file_priv,
2631                                drm_radeon_cmd_header_t header,
2632                                drm_radeon_kcmd_buffer_t *cmdbuf)
2633 {
2634         int id = (int)header.packet.packet_id;
2635         int sz, reg;
2636         RING_LOCALS;
2637
2638         if (id >= RADEON_MAX_STATE_PACKETS)
2639                 return -EINVAL;
2640
2641         sz = packet[id].len;
2642         reg = packet[id].start;
2643
2644         if (sz * sizeof(u32) > drm_buffer_unprocessed(cmdbuf->buffer)) {
2645                 DRM_ERROR("Packet size provided larger than data provided\n");
2646                 return -EINVAL;
2647         }
2648
2649         if (radeon_check_and_fixup_packets(dev_priv, file_priv, id,
2650                                 cmdbuf->buffer)) {
2651                 DRM_ERROR("Packet verification failed\n");
2652                 return -EINVAL;
2653         }
2654
2655         BEGIN_RING(sz + 1);
2656         OUT_RING(CP_PACKET0(reg, (sz - 1)));
2657         OUT_RING_DRM_BUFFER(cmdbuf->buffer, sz);
2658         ADVANCE_RING();
2659
2660         return 0;
2661 }
2662
2663 static __inline__ int radeon_emit_scalars(drm_radeon_private_t *dev_priv,
2664                                           drm_radeon_cmd_header_t header,
2665                                           drm_radeon_kcmd_buffer_t *cmdbuf)
2666 {
2667         int sz = header.scalars.count;
2668         int start = header.scalars.offset;
2669         int stride = header.scalars.stride;
2670         RING_LOCALS;
2671
2672         BEGIN_RING(3 + sz);
2673         OUT_RING(CP_PACKET0(RADEON_SE_TCL_SCALAR_INDX_REG, 0));
2674         OUT_RING(start | (stride << RADEON_SCAL_INDX_DWORD_STRIDE_SHIFT));
2675         OUT_RING(CP_PACKET0_TABLE(RADEON_SE_TCL_SCALAR_DATA_REG, sz - 1));
2676         OUT_RING_DRM_BUFFER(cmdbuf->buffer, sz);
2677         ADVANCE_RING();
2678         return 0;
2679 }
2680
2681 /* God this is ugly
2682  */
2683 static __inline__ int radeon_emit_scalars2(drm_radeon_private_t *dev_priv,
2684                                            drm_radeon_cmd_header_t header,
2685                                            drm_radeon_kcmd_buffer_t *cmdbuf)
2686 {
2687         int sz = header.scalars.count;
2688         int start = ((unsigned int)header.scalars.offset) + 0x100;
2689         int stride = header.scalars.stride;
2690         RING_LOCALS;
2691
2692         BEGIN_RING(3 + sz);
2693         OUT_RING(CP_PACKET0(RADEON_SE_TCL_SCALAR_INDX_REG, 0));
2694         OUT_RING(start | (stride << RADEON_SCAL_INDX_DWORD_STRIDE_SHIFT));
2695         OUT_RING(CP_PACKET0_TABLE(RADEON_SE_TCL_SCALAR_DATA_REG, sz - 1));
2696         OUT_RING_DRM_BUFFER(cmdbuf->buffer, sz);
2697         ADVANCE_RING();
2698         return 0;
2699 }
2700
2701 static __inline__ int radeon_emit_vectors(drm_radeon_private_t *dev_priv,
2702                                           drm_radeon_cmd_header_t header,
2703                                           drm_radeon_kcmd_buffer_t *cmdbuf)
2704 {
2705         int sz = header.vectors.count;
2706         int start = header.vectors.offset;
2707         int stride = header.vectors.stride;
2708         RING_LOCALS;
2709
2710         BEGIN_RING(5 + sz);
2711         OUT_RING_REG(RADEON_SE_TCL_STATE_FLUSH, 0);
2712         OUT_RING(CP_PACKET0(RADEON_SE_TCL_VECTOR_INDX_REG, 0));
2713         OUT_RING(start | (stride << RADEON_VEC_INDX_OCTWORD_STRIDE_SHIFT));
2714         OUT_RING(CP_PACKET0_TABLE(RADEON_SE_TCL_VECTOR_DATA_REG, (sz - 1)));
2715         OUT_RING_DRM_BUFFER(cmdbuf->buffer, sz);
2716         ADVANCE_RING();
2717
2718         return 0;
2719 }
2720
2721 static __inline__ int radeon_emit_veclinear(drm_radeon_private_t *dev_priv,
2722                                           drm_radeon_cmd_header_t header,
2723                                           drm_radeon_kcmd_buffer_t *cmdbuf)
2724 {
2725         int sz = header.veclinear.count * 4;
2726         int start = header.veclinear.addr_lo | (header.veclinear.addr_hi << 8);
2727         RING_LOCALS;
2728
2729         if (!sz)
2730                 return 0;
2731         if (sz * 4 > drm_buffer_unprocessed(cmdbuf->buffer))
2732                 return -EINVAL;
2733
2734         BEGIN_RING(5 + sz);
2735         OUT_RING_REG(RADEON_SE_TCL_STATE_FLUSH, 0);
2736         OUT_RING(CP_PACKET0(RADEON_SE_TCL_VECTOR_INDX_REG, 0));
2737         OUT_RING(start | (1 << RADEON_VEC_INDX_OCTWORD_STRIDE_SHIFT));
2738         OUT_RING(CP_PACKET0_TABLE(RADEON_SE_TCL_VECTOR_DATA_REG, (sz - 1)));
2739         OUT_RING_DRM_BUFFER(cmdbuf->buffer, sz);
2740         ADVANCE_RING();
2741
2742         return 0;
2743 }
2744
2745 static int radeon_emit_packet3(struct drm_device * dev,
2746                                struct drm_file *file_priv,
2747                                drm_radeon_kcmd_buffer_t *cmdbuf)
2748 {
2749         drm_radeon_private_t *dev_priv = dev->dev_private;
2750         unsigned int cmdsz;
2751         int ret;
2752         RING_LOCALS;
2753
2754         DRM_DEBUG("\n");
2755
2756         if ((ret = radeon_check_and_fixup_packet3(dev_priv, file_priv,
2757                                                   cmdbuf, &cmdsz))) {
2758                 DRM_ERROR("Packet verification failed\n");
2759                 return ret;
2760         }
2761
2762         BEGIN_RING(cmdsz);
2763         OUT_RING_DRM_BUFFER(cmdbuf->buffer, cmdsz);
2764         ADVANCE_RING();
2765
2766         return 0;
2767 }
2768
2769 static int radeon_emit_packet3_cliprect(struct drm_device *dev,
2770                                         struct drm_file *file_priv,
2771                                         drm_radeon_kcmd_buffer_t *cmdbuf,
2772                                         int orig_nbox)
2773 {
2774         drm_radeon_private_t *dev_priv = dev->dev_private;
2775         struct drm_clip_rect box;
2776         unsigned int cmdsz;
2777         int ret;
2778         struct drm_clip_rect __user *boxes = cmdbuf->boxes;
2779         int i = 0;
2780         RING_LOCALS;
2781
2782         DRM_DEBUG("\n");
2783
2784         if ((ret = radeon_check_and_fixup_packet3(dev_priv, file_priv,
2785                                                   cmdbuf, &cmdsz))) {
2786                 DRM_ERROR("Packet verification failed\n");
2787                 return ret;
2788         }
2789
2790         if (!orig_nbox)
2791                 goto out;
2792
2793         do {
2794                 if (i < cmdbuf->nbox) {
2795                         if (DRM_COPY_FROM_USER(&box, &boxes[i], sizeof(box)))
2796                                 return -EFAULT;
2797                         /* FIXME The second and subsequent times round
2798                          * this loop, send a WAIT_UNTIL_3D_IDLE before
2799                          * calling emit_clip_rect(). This fixes a
2800                          * lockup on fast machines when sending
2801                          * several cliprects with a cmdbuf, as when
2802                          * waving a 2D window over a 3D
2803                          * window. Something in the commands from user
2804                          * space seems to hang the card when they're
2805                          * sent several times in a row. That would be
2806                          * the correct place to fix it but this works
2807                          * around it until I can figure that out - Tim
2808                          * Smith */
2809                         if (i) {
2810                                 BEGIN_RING(2);
2811                                 RADEON_WAIT_UNTIL_3D_IDLE();
2812                                 ADVANCE_RING();
2813                         }
2814                         radeon_emit_clip_rect(dev_priv, &box);
2815                 }
2816
2817                 BEGIN_RING(cmdsz);
2818                 OUT_RING_DRM_BUFFER(cmdbuf->buffer, cmdsz);
2819                 ADVANCE_RING();
2820
2821         } while (++i < cmdbuf->nbox);
2822         if (cmdbuf->nbox == 1)
2823                 cmdbuf->nbox = 0;
2824
2825         return 0;
2826       out:
2827         drm_buffer_advance(cmdbuf->buffer, cmdsz * 4);
2828         return 0;
2829 }
2830
2831 static int radeon_emit_wait(struct drm_device * dev, int flags)
2832 {
2833         drm_radeon_private_t *dev_priv = dev->dev_private;
2834         RING_LOCALS;
2835
2836         DRM_DEBUG("%x\n", flags);
2837         switch (flags) {
2838         case RADEON_WAIT_2D:
2839                 BEGIN_RING(2);
2840                 RADEON_WAIT_UNTIL_2D_IDLE();
2841                 ADVANCE_RING();
2842                 break;
2843         case RADEON_WAIT_3D:
2844                 BEGIN_RING(2);
2845                 RADEON_WAIT_UNTIL_3D_IDLE();
2846                 ADVANCE_RING();
2847                 break;
2848         case RADEON_WAIT_2D | RADEON_WAIT_3D:
2849                 BEGIN_RING(2);
2850                 RADEON_WAIT_UNTIL_IDLE();
2851                 ADVANCE_RING();
2852                 break;
2853         default:
2854                 return -EINVAL;
2855         }
2856
2857         return 0;
2858 }
2859
2860 static int radeon_cp_cmdbuf(struct drm_device *dev, void *data,
2861                 struct drm_file *file_priv)
2862 {
2863         drm_radeon_private_t *dev_priv = dev->dev_private;
2864         struct drm_device_dma *dma = dev->dma;
2865         struct drm_buf *buf = NULL;
2866         drm_radeon_cmd_header_t stack_header;
2867         int idx;
2868         drm_radeon_kcmd_buffer_t *cmdbuf = data;
2869         int orig_nbox;
2870
2871         LOCK_TEST_WITH_RETURN(dev, file_priv);
2872
2873         RING_SPACE_TEST_WITH_RETURN(dev_priv);
2874         VB_AGE_TEST_WITH_RETURN(dev_priv);
2875
2876         if (cmdbuf->bufsz > 64 * 1024 || cmdbuf->bufsz < 0) {
2877                 return -EINVAL;
2878         }
2879
2880         /* Allocate an in-kernel area and copy in the cmdbuf.  Do this to avoid
2881          * races between checking values and using those values in other code,
2882          * and simply to avoid a lot of function calls to copy in data.
2883          */
2884         if (cmdbuf->bufsz != 0) {
2885                 int rv;
2886                 void __user *buffer = cmdbuf->buffer;
2887                 rv = drm_buffer_alloc(&cmdbuf->buffer, cmdbuf->bufsz);
2888                 if (rv)
2889                         return rv;
2890                 rv = drm_buffer_copy_from_user(cmdbuf->buffer, buffer,
2891                                                 cmdbuf->bufsz);
2892                 if (rv)
2893                         return rv;
2894         }
2895
2896         orig_nbox = cmdbuf->nbox;
2897
2898         if (dev_priv->microcode_version == UCODE_R300) {
2899                 int temp;
2900                 temp = r300_do_cp_cmdbuf(dev, file_priv, cmdbuf);
2901
2902                 if (cmdbuf->bufsz != 0)
2903                         drm_buffer_free(cmdbuf->buffer);
2904
2905                 return temp;
2906         }
2907
2908         /* microcode_version != r300 */
2909         while (drm_buffer_unprocessed(cmdbuf->buffer) >= sizeof(stack_header)) {
2910
2911                 drm_radeon_cmd_header_t *header;
2912                 header = drm_buffer_read_object(cmdbuf->buffer,
2913                                 sizeof(stack_header), &stack_header);
2914
2915                 switch (header->header.cmd_type) {
2916                 case RADEON_CMD_PACKET:
2917                         DRM_DEBUG("RADEON_CMD_PACKET\n");
2918                         if (radeon_emit_packets
2919                             (dev_priv, file_priv, *header, cmdbuf)) {
2920                                 DRM_ERROR("radeon_emit_packets failed\n");
2921                                 goto err;
2922                         }
2923                         break;
2924
2925                 case RADEON_CMD_SCALARS:
2926                         DRM_DEBUG("RADEON_CMD_SCALARS\n");
2927                         if (radeon_emit_scalars(dev_priv, *header, cmdbuf)) {
2928                                 DRM_ERROR("radeon_emit_scalars failed\n");
2929                                 goto err;
2930                         }
2931                         break;
2932
2933                 case RADEON_CMD_VECTORS:
2934                         DRM_DEBUG("RADEON_CMD_VECTORS\n");
2935                         if (radeon_emit_vectors(dev_priv, *header, cmdbuf)) {
2936                                 DRM_ERROR("radeon_emit_vectors failed\n");
2937                                 goto err;
2938                         }
2939                         break;
2940
2941                 case RADEON_CMD_DMA_DISCARD:
2942                         DRM_DEBUG("RADEON_CMD_DMA_DISCARD\n");
2943                         idx = header->dma.buf_idx;
2944                         if (idx < 0 || idx >= dma->buf_count) {
2945                                 DRM_ERROR("buffer index %d (of %d max)\n",
2946                                           idx, dma->buf_count - 1);
2947                                 goto err;
2948                         }
2949
2950                         buf = dma->buflist[idx];
2951                         if (buf->file_priv != file_priv || buf->pending) {
2952                                 DRM_ERROR("bad buffer %p %p %d\n",
2953                                           buf->file_priv, file_priv,
2954                                           buf->pending);
2955                                 goto err;
2956                         }
2957
2958                         radeon_cp_discard_buffer(dev, file_priv->master, buf);
2959                         break;
2960
2961                 case RADEON_CMD_PACKET3:
2962                         DRM_DEBUG("RADEON_CMD_PACKET3\n");
2963                         if (radeon_emit_packet3(dev, file_priv, cmdbuf)) {
2964                                 DRM_ERROR("radeon_emit_packet3 failed\n");
2965                                 goto err;
2966                         }
2967                         break;
2968
2969                 case RADEON_CMD_PACKET3_CLIP:
2970                         DRM_DEBUG("RADEON_CMD_PACKET3_CLIP\n");
2971                         if (radeon_emit_packet3_cliprect
2972                             (dev, file_priv, cmdbuf, orig_nbox)) {
2973                                 DRM_ERROR("radeon_emit_packet3_clip failed\n");
2974                                 goto err;
2975                         }
2976                         break;
2977
2978                 case RADEON_CMD_SCALARS2:
2979                         DRM_DEBUG("RADEON_CMD_SCALARS2\n");
2980                         if (radeon_emit_scalars2(dev_priv, *header, cmdbuf)) {
2981                                 DRM_ERROR("radeon_emit_scalars2 failed\n");
2982                                 goto err;
2983                         }
2984                         break;
2985
2986                 case RADEON_CMD_WAIT:
2987                         DRM_DEBUG("RADEON_CMD_WAIT\n");
2988                         if (radeon_emit_wait(dev, header->wait.flags)) {
2989                                 DRM_ERROR("radeon_emit_wait failed\n");
2990                                 goto err;
2991                         }
2992                         break;
2993                 case RADEON_CMD_VECLINEAR:
2994                         DRM_DEBUG("RADEON_CMD_VECLINEAR\n");
2995                         if (radeon_emit_veclinear(dev_priv, *header, cmdbuf)) {
2996                                 DRM_ERROR("radeon_emit_veclinear failed\n");
2997                                 goto err;
2998                         }
2999                         break;
3000
3001                 default:
3002                         DRM_ERROR("bad cmd_type %d at byte %d\n",
3003                                   header->header.cmd_type,
3004                                   cmdbuf->buffer->iterator);
3005                         goto err;
3006                 }
3007         }
3008
3009         if (cmdbuf->bufsz != 0)
3010                 drm_buffer_free(cmdbuf->buffer);
3011
3012         DRM_DEBUG("DONE\n");
3013         COMMIT_RING();
3014         return 0;
3015
3016       err:
3017         if (cmdbuf->bufsz != 0)
3018                 drm_buffer_free(cmdbuf->buffer);
3019         return -EINVAL;
3020 }
3021
3022 static int radeon_cp_getparam(struct drm_device *dev, void *data, struct drm_file *file_priv)
3023 {
3024         drm_radeon_private_t *dev_priv = dev->dev_private;
3025         drm_radeon_getparam_t *param = data;
3026         int value;
3027
3028         DRM_DEBUG("pid=%d\n", DRM_CURRENTPID);
3029
3030         switch (param->param) {
3031         case RADEON_PARAM_GART_BUFFER_OFFSET:
3032                 value = dev_priv->gart_buffers_offset;
3033                 break;
3034         case RADEON_PARAM_LAST_FRAME:
3035                 dev_priv->stats.last_frame_reads++;
3036                 value = GET_SCRATCH(dev_priv, 0);
3037                 break;
3038         case RADEON_PARAM_LAST_DISPATCH:
3039                 value = GET_SCRATCH(dev_priv, 1);
3040                 break;
3041         case RADEON_PARAM_LAST_CLEAR:
3042                 dev_priv->stats.last_clear_reads++;
3043                 value = GET_SCRATCH(dev_priv, 2);
3044                 break;
3045         case RADEON_PARAM_IRQ_NR:
3046                 if ((dev_priv->flags & RADEON_FAMILY_MASK) >= CHIP_R600)
3047                         value = 0;
3048                 else
3049                         value = drm_dev_to_irq(dev);
3050                 break;
3051         case RADEON_PARAM_GART_BASE:
3052                 value = dev_priv->gart_vm_start;
3053                 break;
3054         case RADEON_PARAM_REGISTER_HANDLE:
3055                 value = dev_priv->mmio->offset;
3056                 break;
3057         case RADEON_PARAM_STATUS_HANDLE:
3058                 value = dev_priv->ring_rptr_offset;
3059                 break;
3060 #if BITS_PER_LONG == 32
3061                 /*
3062                  * This ioctl() doesn't work on 64-bit platforms because hw_lock is a
3063                  * pointer which can't fit into an int-sized variable.  According to
3064                  * Michel Dänzer, the ioctl() is only used on embedded platforms, so
3065                  * not supporting it shouldn't be a problem.  If the same functionality
3066                  * is needed on 64-bit platforms, a new ioctl() would have to be added,
3067                  * so backwards-compatibility for the embedded platforms can be
3068                  * maintained.  --davidm 4-Feb-2004.
3069                  */
3070         case RADEON_PARAM_SAREA_HANDLE:
3071                 /* The lock is the first dword in the sarea. */
3072                 /* no users of this parameter */
3073                 break;
3074 #endif
3075         case RADEON_PARAM_GART_TEX_HANDLE:
3076                 value = dev_priv->gart_textures_offset;
3077                 break;
3078         case RADEON_PARAM_SCRATCH_OFFSET:
3079                 if (!dev_priv->writeback_works)
3080                         return -EINVAL;
3081                 if ((dev_priv->flags & RADEON_FAMILY_MASK) >= CHIP_R600)
3082                         value = R600_SCRATCH_REG_OFFSET;
3083                 else
3084                         value = RADEON_SCRATCH_REG_OFFSET;
3085                 break;
3086         case RADEON_PARAM_CARD_TYPE:
3087                 if (dev_priv->flags & RADEON_IS_PCIE)
3088                         value = RADEON_CARD_PCIE;
3089                 else if (dev_priv->flags & RADEON_IS_AGP)
3090                         value = RADEON_CARD_AGP;
3091                 else
3092                         value = RADEON_CARD_PCI;
3093                 break;
3094         case RADEON_PARAM_VBLANK_CRTC:
3095                 value = radeon_vblank_crtc_get(dev);
3096                 break;
3097         case RADEON_PARAM_FB_LOCATION:
3098                 value = radeon_read_fb_location(dev_priv);
3099                 break;
3100         case RADEON_PARAM_NUM_GB_PIPES:
3101                 value = dev_priv->num_gb_pipes;
3102                 break;
3103         case RADEON_PARAM_NUM_Z_PIPES:
3104                 value = dev_priv->num_z_pipes;
3105                 break;
3106         default:
3107                 DRM_DEBUG("Invalid parameter %d\n", param->param);
3108                 return -EINVAL;
3109         }
3110
3111         if (DRM_COPY_TO_USER(param->value, &value, sizeof(int))) {
3112                 DRM_ERROR("copy_to_user\n");
3113                 return -EFAULT;
3114         }
3115
3116         return 0;
3117 }
3118
3119 static int radeon_cp_setparam(struct drm_device *dev, void *data, struct drm_file *file_priv)
3120 {
3121         drm_radeon_private_t *dev_priv = dev->dev_private;
3122         struct drm_radeon_master_private *master_priv = file_priv->master->driver_priv;
3123         drm_radeon_setparam_t *sp = data;
3124         struct drm_radeon_driver_file_fields *radeon_priv;
3125
3126         switch (sp->param) {
3127         case RADEON_SETPARAM_FB_LOCATION:
3128                 radeon_priv = file_priv->driver_priv;
3129                 radeon_priv->radeon_fb_delta = dev_priv->fb_location -
3130                     sp->value;
3131                 break;
3132         case RADEON_SETPARAM_SWITCH_TILING:
3133                 if (sp->value == 0) {
3134                         DRM_DEBUG("color tiling disabled\n");
3135                         dev_priv->front_pitch_offset &= ~RADEON_DST_TILE_MACRO;
3136                         dev_priv->back_pitch_offset &= ~RADEON_DST_TILE_MACRO;
3137                         if (master_priv->sarea_priv)
3138                                 master_priv->sarea_priv->tiling_enabled = 0;
3139                 } else if (sp->value == 1) {
3140                         DRM_DEBUG("color tiling enabled\n");
3141                         dev_priv->front_pitch_offset |= RADEON_DST_TILE_MACRO;
3142                         dev_priv->back_pitch_offset |= RADEON_DST_TILE_MACRO;
3143                         if (master_priv->sarea_priv)
3144                                 master_priv->sarea_priv->tiling_enabled = 1;
3145                 }
3146                 break;
3147         case RADEON_SETPARAM_PCIGART_LOCATION:
3148                 dev_priv->pcigart_offset = sp->value;
3149                 dev_priv->pcigart_offset_set = 1;
3150                 break;
3151         case RADEON_SETPARAM_NEW_MEMMAP:
3152                 dev_priv->new_memmap = sp->value;
3153                 break;
3154         case RADEON_SETPARAM_PCIGART_TABLE_SIZE:
3155                 dev_priv->gart_info.table_size = sp->value;
3156                 if (dev_priv->gart_info.table_size < RADEON_PCIGART_TABLE_SIZE)
3157                         dev_priv->gart_info.table_size = RADEON_PCIGART_TABLE_SIZE;
3158                 break;
3159         case RADEON_SETPARAM_VBLANK_CRTC:
3160                 return radeon_vblank_crtc_set(dev, sp->value);
3161                 break;
3162         default:
3163                 DRM_DEBUG("Invalid parameter %d\n", sp->param);
3164                 return -EINVAL;
3165         }
3166
3167         return 0;
3168 }
3169
3170 /* When a client dies:
3171  *    - Check for and clean up flipped page state
3172  *    - Free any alloced GART memory.
3173  *    - Free any alloced radeon surfaces.
3174  *
3175  * DRM infrastructure takes care of reclaiming dma buffers.
3176  */
3177 void radeon_driver_preclose(struct drm_device *dev, struct drm_file *file_priv)
3178 {
3179         if (dev->dev_private) {
3180                 drm_radeon_private_t *dev_priv = dev->dev_private;
3181                 dev_priv->page_flipping = 0;
3182                 radeon_mem_release(file_priv, dev_priv->gart_heap);
3183                 radeon_mem_release(file_priv, dev_priv->fb_heap);
3184                 radeon_surfaces_release(file_priv, dev_priv);
3185         }
3186 }
3187
3188 void radeon_driver_lastclose(struct drm_device *dev)
3189 {
3190         radeon_surfaces_release(PCIGART_FILE_PRIV, dev->dev_private);
3191         radeon_do_release(dev);
3192 }
3193
3194 int radeon_driver_open(struct drm_device *dev, struct drm_file *file_priv)
3195 {
3196         drm_radeon_private_t *dev_priv = dev->dev_private;
3197         struct drm_radeon_driver_file_fields *radeon_priv;
3198
3199         DRM_DEBUG("\n");
3200         radeon_priv = kmalloc(sizeof(*radeon_priv), GFP_KERNEL);
3201
3202         if (!radeon_priv)
3203                 return -ENOMEM;
3204
3205         file_priv->driver_priv = radeon_priv;
3206
3207         if (dev_priv)
3208                 radeon_priv->radeon_fb_delta = dev_priv->fb_location;
3209         else
3210                 radeon_priv->radeon_fb_delta = 0;
3211         return 0;
3212 }
3213
3214 void radeon_driver_postclose(struct drm_device *dev, struct drm_file *file_priv)
3215 {
3216         struct drm_radeon_driver_file_fields *radeon_priv =
3217             file_priv->driver_priv;
3218
3219         kfree(radeon_priv);
3220 }
3221
3222 struct drm_ioctl_desc radeon_ioctls[] = {
3223         DRM_IOCTL_DEF(DRM_RADEON_CP_INIT, radeon_cp_init, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
3224         DRM_IOCTL_DEF(DRM_RADEON_CP_START, radeon_cp_start, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
3225         DRM_IOCTL_DEF(DRM_RADEON_CP_STOP, radeon_cp_stop, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
3226         DRM_IOCTL_DEF(DRM_RADEON_CP_RESET, radeon_cp_reset, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
3227         DRM_IOCTL_DEF(DRM_RADEON_CP_IDLE, radeon_cp_idle, DRM_AUTH),
3228         DRM_IOCTL_DEF(DRM_RADEON_CP_RESUME, radeon_cp_resume, DRM_AUTH),
3229         DRM_IOCTL_DEF(DRM_RADEON_RESET, radeon_engine_reset, DRM_AUTH),
3230         DRM_IOCTL_DEF(DRM_RADEON_FULLSCREEN, radeon_fullscreen, DRM_AUTH),
3231         DRM_IOCTL_DEF(DRM_RADEON_SWAP, radeon_cp_swap, DRM_AUTH),
3232         DRM_IOCTL_DEF(DRM_RADEON_CLEAR, radeon_cp_clear, DRM_AUTH),
3233         DRM_IOCTL_DEF(DRM_RADEON_VERTEX, radeon_cp_vertex, DRM_AUTH),
3234         DRM_IOCTL_DEF(DRM_RADEON_INDICES, radeon_cp_indices, DRM_AUTH),
3235         DRM_IOCTL_DEF(DRM_RADEON_TEXTURE, radeon_cp_texture, DRM_AUTH),
3236         DRM_IOCTL_DEF(DRM_RADEON_STIPPLE, radeon_cp_stipple, DRM_AUTH),
3237         DRM_IOCTL_DEF(DRM_RADEON_INDIRECT, radeon_cp_indirect, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
3238         DRM_IOCTL_DEF(DRM_RADEON_VERTEX2, radeon_cp_vertex2, DRM_AUTH),
3239         DRM_IOCTL_DEF(DRM_RADEON_CMDBUF, radeon_cp_cmdbuf, DRM_AUTH),
3240         DRM_IOCTL_DEF(DRM_RADEON_GETPARAM, radeon_cp_getparam, DRM_AUTH),
3241         DRM_IOCTL_DEF(DRM_RADEON_FLIP, radeon_cp_flip, DRM_AUTH),
3242         DRM_IOCTL_DEF(DRM_RADEON_ALLOC, radeon_mem_alloc, DRM_AUTH),
3243         DRM_IOCTL_DEF(DRM_RADEON_FREE, radeon_mem_free, DRM_AUTH),
3244         DRM_IOCTL_DEF(DRM_RADEON_INIT_HEAP, radeon_mem_init_heap, DRM_AUTH|DRM_MASTER|DRM_ROOT_ONLY),
3245         DRM_IOCTL_DEF(DRM_RADEON_IRQ_EMIT, radeon_irq_emit, DRM_AUTH),
3246         DRM_IOCTL_DEF(DRM_RADEON_IRQ_WAIT, radeon_irq_wait, DRM_AUTH),
3247         DRM_IOCTL_DEF(DRM_RADEON_SETPARAM, radeon_cp_setparam, DRM_AUTH),
3248         DRM_IOCTL_DEF(DRM_RADEON_SURF_ALLOC, radeon_surface_alloc, DRM_AUTH),
3249         DRM_IOCTL_DEF(DRM_RADEON_SURF_FREE, radeon_surface_free, DRM_AUTH),
3250         DRM_IOCTL_DEF(DRM_RADEON_CS, r600_cs_legacy_ioctl, DRM_AUTH)
3251 };
3252
3253 int radeon_max_ioctl = DRM_ARRAY_SIZE(radeon_ioctls);