]> git.karo-electronics.de Git - mv-sheeva.git/blob - drivers/gpu/drm/nouveau/nv04_graph.c
drm/nouveau: store engine type in gpuobj class structs
[mv-sheeva.git] / drivers / gpu / drm / nouveau / nv04_graph.c
1 /*
2  * Copyright 2007 Stephane Marchesin
3  * All Rights Reserved.
4  *
5  * Permission is hereby granted, free of charge, to any person obtaining a
6  * copy of this software and associated documentation files (the "Software"),
7  * to deal in the Software without restriction, including without limitation
8  * the rights to use, copy, modify, merge, publish, distribute, sublicense,
9  * and/or sell copies of the Software, and to permit persons to whom the
10  * Software is furnished to do so, subject to the following conditions:
11  *
12  * The above copyright notice and this permission notice (including the next
13  * paragraph) shall be included in all copies or substantial portions of the
14  * Software.
15  *
16  * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17  * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18  * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
19  * PRECISION INSIGHT AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM, DAMAGES OR
20  * OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
21  * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
22  * DEALINGS IN THE SOFTWARE.
23  */
24
25 #include "drmP.h"
26 #include "drm.h"
27 #include "nouveau_drm.h"
28 #include "nouveau_drv.h"
29
30 static uint32_t nv04_graph_ctx_regs[] = {
31         0x0040053c,
32         0x00400544,
33         0x00400540,
34         0x00400548,
35         NV04_PGRAPH_CTX_SWITCH1,
36         NV04_PGRAPH_CTX_SWITCH2,
37         NV04_PGRAPH_CTX_SWITCH3,
38         NV04_PGRAPH_CTX_SWITCH4,
39         NV04_PGRAPH_CTX_CACHE1,
40         NV04_PGRAPH_CTX_CACHE2,
41         NV04_PGRAPH_CTX_CACHE3,
42         NV04_PGRAPH_CTX_CACHE4,
43         0x00400184,
44         0x004001a4,
45         0x004001c4,
46         0x004001e4,
47         0x00400188,
48         0x004001a8,
49         0x004001c8,
50         0x004001e8,
51         0x0040018c,
52         0x004001ac,
53         0x004001cc,
54         0x004001ec,
55         0x00400190,
56         0x004001b0,
57         0x004001d0,
58         0x004001f0,
59         0x00400194,
60         0x004001b4,
61         0x004001d4,
62         0x004001f4,
63         0x00400198,
64         0x004001b8,
65         0x004001d8,
66         0x004001f8,
67         0x0040019c,
68         0x004001bc,
69         0x004001dc,
70         0x004001fc,
71         0x00400174,
72         NV04_PGRAPH_DMA_START_0,
73         NV04_PGRAPH_DMA_START_1,
74         NV04_PGRAPH_DMA_LENGTH,
75         NV04_PGRAPH_DMA_MISC,
76         NV04_PGRAPH_DMA_PITCH,
77         NV04_PGRAPH_BOFFSET0,
78         NV04_PGRAPH_BBASE0,
79         NV04_PGRAPH_BLIMIT0,
80         NV04_PGRAPH_BOFFSET1,
81         NV04_PGRAPH_BBASE1,
82         NV04_PGRAPH_BLIMIT1,
83         NV04_PGRAPH_BOFFSET2,
84         NV04_PGRAPH_BBASE2,
85         NV04_PGRAPH_BLIMIT2,
86         NV04_PGRAPH_BOFFSET3,
87         NV04_PGRAPH_BBASE3,
88         NV04_PGRAPH_BLIMIT3,
89         NV04_PGRAPH_BOFFSET4,
90         NV04_PGRAPH_BBASE4,
91         NV04_PGRAPH_BLIMIT4,
92         NV04_PGRAPH_BOFFSET5,
93         NV04_PGRAPH_BBASE5,
94         NV04_PGRAPH_BLIMIT5,
95         NV04_PGRAPH_BPITCH0,
96         NV04_PGRAPH_BPITCH1,
97         NV04_PGRAPH_BPITCH2,
98         NV04_PGRAPH_BPITCH3,
99         NV04_PGRAPH_BPITCH4,
100         NV04_PGRAPH_SURFACE,
101         NV04_PGRAPH_STATE,
102         NV04_PGRAPH_BSWIZZLE2,
103         NV04_PGRAPH_BSWIZZLE5,
104         NV04_PGRAPH_BPIXEL,
105         NV04_PGRAPH_NOTIFY,
106         NV04_PGRAPH_PATT_COLOR0,
107         NV04_PGRAPH_PATT_COLOR1,
108         NV04_PGRAPH_PATT_COLORRAM+0x00,
109         NV04_PGRAPH_PATT_COLORRAM+0x04,
110         NV04_PGRAPH_PATT_COLORRAM+0x08,
111         NV04_PGRAPH_PATT_COLORRAM+0x0c,
112         NV04_PGRAPH_PATT_COLORRAM+0x10,
113         NV04_PGRAPH_PATT_COLORRAM+0x14,
114         NV04_PGRAPH_PATT_COLORRAM+0x18,
115         NV04_PGRAPH_PATT_COLORRAM+0x1c,
116         NV04_PGRAPH_PATT_COLORRAM+0x20,
117         NV04_PGRAPH_PATT_COLORRAM+0x24,
118         NV04_PGRAPH_PATT_COLORRAM+0x28,
119         NV04_PGRAPH_PATT_COLORRAM+0x2c,
120         NV04_PGRAPH_PATT_COLORRAM+0x30,
121         NV04_PGRAPH_PATT_COLORRAM+0x34,
122         NV04_PGRAPH_PATT_COLORRAM+0x38,
123         NV04_PGRAPH_PATT_COLORRAM+0x3c,
124         NV04_PGRAPH_PATT_COLORRAM+0x40,
125         NV04_PGRAPH_PATT_COLORRAM+0x44,
126         NV04_PGRAPH_PATT_COLORRAM+0x48,
127         NV04_PGRAPH_PATT_COLORRAM+0x4c,
128         NV04_PGRAPH_PATT_COLORRAM+0x50,
129         NV04_PGRAPH_PATT_COLORRAM+0x54,
130         NV04_PGRAPH_PATT_COLORRAM+0x58,
131         NV04_PGRAPH_PATT_COLORRAM+0x5c,
132         NV04_PGRAPH_PATT_COLORRAM+0x60,
133         NV04_PGRAPH_PATT_COLORRAM+0x64,
134         NV04_PGRAPH_PATT_COLORRAM+0x68,
135         NV04_PGRAPH_PATT_COLORRAM+0x6c,
136         NV04_PGRAPH_PATT_COLORRAM+0x70,
137         NV04_PGRAPH_PATT_COLORRAM+0x74,
138         NV04_PGRAPH_PATT_COLORRAM+0x78,
139         NV04_PGRAPH_PATT_COLORRAM+0x7c,
140         NV04_PGRAPH_PATT_COLORRAM+0x80,
141         NV04_PGRAPH_PATT_COLORRAM+0x84,
142         NV04_PGRAPH_PATT_COLORRAM+0x88,
143         NV04_PGRAPH_PATT_COLORRAM+0x8c,
144         NV04_PGRAPH_PATT_COLORRAM+0x90,
145         NV04_PGRAPH_PATT_COLORRAM+0x94,
146         NV04_PGRAPH_PATT_COLORRAM+0x98,
147         NV04_PGRAPH_PATT_COLORRAM+0x9c,
148         NV04_PGRAPH_PATT_COLORRAM+0xa0,
149         NV04_PGRAPH_PATT_COLORRAM+0xa4,
150         NV04_PGRAPH_PATT_COLORRAM+0xa8,
151         NV04_PGRAPH_PATT_COLORRAM+0xac,
152         NV04_PGRAPH_PATT_COLORRAM+0xb0,
153         NV04_PGRAPH_PATT_COLORRAM+0xb4,
154         NV04_PGRAPH_PATT_COLORRAM+0xb8,
155         NV04_PGRAPH_PATT_COLORRAM+0xbc,
156         NV04_PGRAPH_PATT_COLORRAM+0xc0,
157         NV04_PGRAPH_PATT_COLORRAM+0xc4,
158         NV04_PGRAPH_PATT_COLORRAM+0xc8,
159         NV04_PGRAPH_PATT_COLORRAM+0xcc,
160         NV04_PGRAPH_PATT_COLORRAM+0xd0,
161         NV04_PGRAPH_PATT_COLORRAM+0xd4,
162         NV04_PGRAPH_PATT_COLORRAM+0xd8,
163         NV04_PGRAPH_PATT_COLORRAM+0xdc,
164         NV04_PGRAPH_PATT_COLORRAM+0xe0,
165         NV04_PGRAPH_PATT_COLORRAM+0xe4,
166         NV04_PGRAPH_PATT_COLORRAM+0xe8,
167         NV04_PGRAPH_PATT_COLORRAM+0xec,
168         NV04_PGRAPH_PATT_COLORRAM+0xf0,
169         NV04_PGRAPH_PATT_COLORRAM+0xf4,
170         NV04_PGRAPH_PATT_COLORRAM+0xf8,
171         NV04_PGRAPH_PATT_COLORRAM+0xfc,
172         NV04_PGRAPH_PATTERN,
173         0x0040080c,
174         NV04_PGRAPH_PATTERN_SHAPE,
175         0x00400600,
176         NV04_PGRAPH_ROP3,
177         NV04_PGRAPH_CHROMA,
178         NV04_PGRAPH_BETA_AND,
179         NV04_PGRAPH_BETA_PREMULT,
180         NV04_PGRAPH_CONTROL0,
181         NV04_PGRAPH_CONTROL1,
182         NV04_PGRAPH_CONTROL2,
183         NV04_PGRAPH_BLEND,
184         NV04_PGRAPH_STORED_FMT,
185         NV04_PGRAPH_SOURCE_COLOR,
186         0x00400560,
187         0x00400568,
188         0x00400564,
189         0x0040056c,
190         0x00400400,
191         0x00400480,
192         0x00400404,
193         0x00400484,
194         0x00400408,
195         0x00400488,
196         0x0040040c,
197         0x0040048c,
198         0x00400410,
199         0x00400490,
200         0x00400414,
201         0x00400494,
202         0x00400418,
203         0x00400498,
204         0x0040041c,
205         0x0040049c,
206         0x00400420,
207         0x004004a0,
208         0x00400424,
209         0x004004a4,
210         0x00400428,
211         0x004004a8,
212         0x0040042c,
213         0x004004ac,
214         0x00400430,
215         0x004004b0,
216         0x00400434,
217         0x004004b4,
218         0x00400438,
219         0x004004b8,
220         0x0040043c,
221         0x004004bc,
222         0x00400440,
223         0x004004c0,
224         0x00400444,
225         0x004004c4,
226         0x00400448,
227         0x004004c8,
228         0x0040044c,
229         0x004004cc,
230         0x00400450,
231         0x004004d0,
232         0x00400454,
233         0x004004d4,
234         0x00400458,
235         0x004004d8,
236         0x0040045c,
237         0x004004dc,
238         0x00400460,
239         0x004004e0,
240         0x00400464,
241         0x004004e4,
242         0x00400468,
243         0x004004e8,
244         0x0040046c,
245         0x004004ec,
246         0x00400470,
247         0x004004f0,
248         0x00400474,
249         0x004004f4,
250         0x00400478,
251         0x004004f8,
252         0x0040047c,
253         0x004004fc,
254         0x00400534,
255         0x00400538,
256         0x00400514,
257         0x00400518,
258         0x0040051c,
259         0x00400520,
260         0x00400524,
261         0x00400528,
262         0x0040052c,
263         0x00400530,
264         0x00400d00,
265         0x00400d40,
266         0x00400d80,
267         0x00400d04,
268         0x00400d44,
269         0x00400d84,
270         0x00400d08,
271         0x00400d48,
272         0x00400d88,
273         0x00400d0c,
274         0x00400d4c,
275         0x00400d8c,
276         0x00400d10,
277         0x00400d50,
278         0x00400d90,
279         0x00400d14,
280         0x00400d54,
281         0x00400d94,
282         0x00400d18,
283         0x00400d58,
284         0x00400d98,
285         0x00400d1c,
286         0x00400d5c,
287         0x00400d9c,
288         0x00400d20,
289         0x00400d60,
290         0x00400da0,
291         0x00400d24,
292         0x00400d64,
293         0x00400da4,
294         0x00400d28,
295         0x00400d68,
296         0x00400da8,
297         0x00400d2c,
298         0x00400d6c,
299         0x00400dac,
300         0x00400d30,
301         0x00400d70,
302         0x00400db0,
303         0x00400d34,
304         0x00400d74,
305         0x00400db4,
306         0x00400d38,
307         0x00400d78,
308         0x00400db8,
309         0x00400d3c,
310         0x00400d7c,
311         0x00400dbc,
312         0x00400590,
313         0x00400594,
314         0x00400598,
315         0x0040059c,
316         0x004005a8,
317         0x004005ac,
318         0x004005b0,
319         0x004005b4,
320         0x004005c0,
321         0x004005c4,
322         0x004005c8,
323         0x004005cc,
324         0x004005d0,
325         0x004005d4,
326         0x004005d8,
327         0x004005dc,
328         0x004005e0,
329         NV04_PGRAPH_PASSTHRU_0,
330         NV04_PGRAPH_PASSTHRU_1,
331         NV04_PGRAPH_PASSTHRU_2,
332         NV04_PGRAPH_DVD_COLORFMT,
333         NV04_PGRAPH_SCALED_FORMAT,
334         NV04_PGRAPH_MISC24_0,
335         NV04_PGRAPH_MISC24_1,
336         NV04_PGRAPH_MISC24_2,
337         0x00400500,
338         0x00400504,
339         NV04_PGRAPH_VALID1,
340         NV04_PGRAPH_VALID2,
341         NV04_PGRAPH_DEBUG_3
342 };
343
344 struct graph_state {
345         uint32_t nv04[ARRAY_SIZE(nv04_graph_ctx_regs)];
346 };
347
348 struct nouveau_channel *
349 nv04_graph_channel(struct drm_device *dev)
350 {
351         struct drm_nouveau_private *dev_priv = dev->dev_private;
352         int chid = dev_priv->engine.fifo.channels;
353
354         if (nv_rd32(dev, NV04_PGRAPH_CTX_CONTROL) & 0x00010000)
355                 chid = nv_rd32(dev, NV04_PGRAPH_CTX_USER) >> 24;
356
357         if (chid >= dev_priv->engine.fifo.channels)
358                 return NULL;
359
360         return dev_priv->channels.ptr[chid];
361 }
362
363 void
364 nv04_graph_context_switch(struct drm_device *dev)
365 {
366         struct drm_nouveau_private *dev_priv = dev->dev_private;
367         struct nouveau_pgraph_engine *pgraph = &dev_priv->engine.graph;
368         struct nouveau_channel *chan = NULL;
369         int chid;
370
371         pgraph->fifo_access(dev, false);
372         nouveau_wait_for_idle(dev);
373
374         /* If previous context is valid, we need to save it */
375         pgraph->unload_context(dev);
376
377         /* Load context for next channel */
378         chid = dev_priv->engine.fifo.channel_id(dev);
379         chan = dev_priv->channels.ptr[chid];
380         if (chan)
381                 nv04_graph_load_context(chan);
382
383         pgraph->fifo_access(dev, true);
384 }
385
386 static uint32_t *ctx_reg(struct graph_state *ctx, uint32_t reg)
387 {
388         int i;
389
390         for (i = 0; i < ARRAY_SIZE(nv04_graph_ctx_regs); i++) {
391                 if (nv04_graph_ctx_regs[i] == reg)
392                         return &ctx->nv04[i];
393         }
394
395         return NULL;
396 }
397
398 int nv04_graph_create_context(struct nouveau_channel *chan)
399 {
400         struct graph_state *pgraph_ctx;
401         NV_DEBUG(chan->dev, "nv04_graph_context_create %d\n", chan->id);
402
403         chan->pgraph_ctx = pgraph_ctx = kzalloc(sizeof(*pgraph_ctx),
404                                                 GFP_KERNEL);
405         if (pgraph_ctx == NULL)
406                 return -ENOMEM;
407
408         *ctx_reg(pgraph_ctx, NV04_PGRAPH_DEBUG_3) = 0xfad4ff31;
409
410         return 0;
411 }
412
413 void nv04_graph_destroy_context(struct nouveau_channel *chan)
414 {
415         struct drm_device *dev = chan->dev;
416         struct drm_nouveau_private *dev_priv = dev->dev_private;
417         struct nouveau_pgraph_engine *pgraph = &dev_priv->engine.graph;
418         struct graph_state *pgraph_ctx = chan->pgraph_ctx;
419         unsigned long flags;
420
421         spin_lock_irqsave(&dev_priv->context_switch_lock, flags);
422         pgraph->fifo_access(dev, false);
423
424         /* Unload the context if it's the currently active one */
425         if (pgraph->channel(dev) == chan)
426                 pgraph->unload_context(dev);
427
428         /* Free the context resources */
429         kfree(pgraph_ctx);
430         chan->pgraph_ctx = NULL;
431
432         pgraph->fifo_access(dev, true);
433         spin_unlock_irqrestore(&dev_priv->context_switch_lock, flags);
434 }
435
436 int nv04_graph_load_context(struct nouveau_channel *chan)
437 {
438         struct drm_device *dev = chan->dev;
439         struct graph_state *pgraph_ctx = chan->pgraph_ctx;
440         uint32_t tmp;
441         int i;
442
443         for (i = 0; i < ARRAY_SIZE(nv04_graph_ctx_regs); i++)
444                 nv_wr32(dev, nv04_graph_ctx_regs[i], pgraph_ctx->nv04[i]);
445
446         nv_wr32(dev, NV04_PGRAPH_CTX_CONTROL, 0x10010100);
447
448         tmp  = nv_rd32(dev, NV04_PGRAPH_CTX_USER) & 0x00ffffff;
449         nv_wr32(dev, NV04_PGRAPH_CTX_USER, tmp | chan->id << 24);
450
451         tmp = nv_rd32(dev, NV04_PGRAPH_FFINTFC_ST2);
452         nv_wr32(dev, NV04_PGRAPH_FFINTFC_ST2, tmp & 0x000fffff);
453
454         return 0;
455 }
456
457 int
458 nv04_graph_unload_context(struct drm_device *dev)
459 {
460         struct drm_nouveau_private *dev_priv = dev->dev_private;
461         struct nouveau_pgraph_engine *pgraph = &dev_priv->engine.graph;
462         struct nouveau_channel *chan = NULL;
463         struct graph_state *ctx;
464         uint32_t tmp;
465         int i;
466
467         chan = pgraph->channel(dev);
468         if (!chan)
469                 return 0;
470         ctx = chan->pgraph_ctx;
471
472         for (i = 0; i < ARRAY_SIZE(nv04_graph_ctx_regs); i++)
473                 ctx->nv04[i] = nv_rd32(dev, nv04_graph_ctx_regs[i]);
474
475         nv_wr32(dev, NV04_PGRAPH_CTX_CONTROL, 0x10000000);
476         tmp  = nv_rd32(dev, NV04_PGRAPH_CTX_USER) & 0x00ffffff;
477         tmp |= (dev_priv->engine.fifo.channels - 1) << 24;
478         nv_wr32(dev, NV04_PGRAPH_CTX_USER, tmp);
479         return 0;
480 }
481
482 int nv04_graph_init(struct drm_device *dev)
483 {
484         struct drm_nouveau_private *dev_priv = dev->dev_private;
485         uint32_t tmp;
486
487         nv_wr32(dev, NV03_PMC_ENABLE, nv_rd32(dev, NV03_PMC_ENABLE) &
488                         ~NV_PMC_ENABLE_PGRAPH);
489         nv_wr32(dev, NV03_PMC_ENABLE, nv_rd32(dev, NV03_PMC_ENABLE) |
490                          NV_PMC_ENABLE_PGRAPH);
491
492         /* Enable PGRAPH interrupts */
493         nv_wr32(dev, NV03_PGRAPH_INTR, 0xFFFFFFFF);
494         nv_wr32(dev, NV03_PGRAPH_INTR_EN, 0xFFFFFFFF);
495
496         nv_wr32(dev, NV04_PGRAPH_VALID1, 0);
497         nv_wr32(dev, NV04_PGRAPH_VALID2, 0);
498         /*nv_wr32(dev, NV04_PGRAPH_DEBUG_0, 0x000001FF);
499         nv_wr32(dev, NV04_PGRAPH_DEBUG_0, 0x001FFFFF);*/
500         nv_wr32(dev, NV04_PGRAPH_DEBUG_0, 0x1231c000);
501         /*1231C000 blob, 001 haiku*/
502         //*V_WRITE(NV04_PGRAPH_DEBUG_1, 0xf2d91100);*/
503         nv_wr32(dev, NV04_PGRAPH_DEBUG_1, 0x72111100);
504         /*0x72111100 blob , 01 haiku*/
505         /*nv_wr32(dev, NV04_PGRAPH_DEBUG_2, 0x11d5f870);*/
506         nv_wr32(dev, NV04_PGRAPH_DEBUG_2, 0x11d5f071);
507         /*haiku same*/
508
509         /*nv_wr32(dev, NV04_PGRAPH_DEBUG_3, 0xfad4ff31);*/
510         nv_wr32(dev, NV04_PGRAPH_DEBUG_3, 0xf0d4ff31);
511         /*haiku and blob 10d4*/
512
513         nv_wr32(dev, NV04_PGRAPH_STATE        , 0xFFFFFFFF);
514         nv_wr32(dev, NV04_PGRAPH_CTX_CONTROL  , 0x10000100);
515         tmp  = nv_rd32(dev, NV04_PGRAPH_CTX_USER) & 0x00ffffff;
516         tmp |= (dev_priv->engine.fifo.channels - 1) << 24;
517         nv_wr32(dev, NV04_PGRAPH_CTX_USER, tmp);
518
519         /* These don't belong here, they're part of a per-channel context */
520         nv_wr32(dev, NV04_PGRAPH_PATTERN_SHAPE, 0x00000000);
521         nv_wr32(dev, NV04_PGRAPH_BETA_AND     , 0xFFFFFFFF);
522
523         return 0;
524 }
525
526 void nv04_graph_takedown(struct drm_device *dev)
527 {
528 }
529
530 void
531 nv04_graph_fifo_access(struct drm_device *dev, bool enabled)
532 {
533         if (enabled)
534                 nv_wr32(dev, NV04_PGRAPH_FIFO,
535                                         nv_rd32(dev, NV04_PGRAPH_FIFO) | 1);
536         else
537                 nv_wr32(dev, NV04_PGRAPH_FIFO,
538                                         nv_rd32(dev, NV04_PGRAPH_FIFO) & ~1);
539 }
540
541 static int
542 nv04_graph_mthd_set_ref(struct nouveau_channel *chan, int grclass,
543                         int mthd, uint32_t data)
544 {
545         atomic_set(&chan->fence.last_sequence_irq, data);
546         return 0;
547 }
548
549 /*
550  * Software methods, why they are needed, and how they all work:
551  *
552  * NV04 and NV05 keep most of the state in PGRAPH context itself, but some
553  * 2d engine settings are kept inside the grobjs themselves. The grobjs are
554  * 3 words long on both. grobj format on NV04 is:
555  *
556  * word 0:
557  *  - bits 0-7: class
558  *  - bit 12: color key active
559  *  - bit 13: clip rect active
560  *  - bit 14: if set, destination surface is swizzled and taken from buffer 5
561  *            [set by NV04_SWIZZLED_SURFACE], otherwise it's linear and taken
562  *            from buffer 0 [set by NV04_CONTEXT_SURFACES_2D or
563  *            NV03_CONTEXT_SURFACE_DST].
564  *  - bits 15-17: 2d operation [aka patch config]
565  *  - bit 24: patch valid [enables rendering using this object]
566  *  - bit 25: surf3d valid [for tex_tri and multitex_tri only]
567  * word 1:
568  *  - bits 0-1: mono format
569  *  - bits 8-13: color format
570  *  - bits 16-31: DMA_NOTIFY instance
571  * word 2:
572  *  - bits 0-15: DMA_A instance
573  *  - bits 16-31: DMA_B instance
574  *
575  * On NV05 it's:
576  *
577  * word 0:
578  *  - bits 0-7: class
579  *  - bit 12: color key active
580  *  - bit 13: clip rect active
581  *  - bit 14: if set, destination surface is swizzled and taken from buffer 5
582  *            [set by NV04_SWIZZLED_SURFACE], otherwise it's linear and taken
583  *            from buffer 0 [set by NV04_CONTEXT_SURFACES_2D or
584  *            NV03_CONTEXT_SURFACE_DST].
585  *  - bits 15-17: 2d operation [aka patch config]
586  *  - bits 20-22: dither mode
587  *  - bit 24: patch valid [enables rendering using this object]
588  *  - bit 25: surface_dst/surface_color/surf2d/surf3d valid
589  *  - bit 26: surface_src/surface_zeta valid
590  *  - bit 27: pattern valid
591  *  - bit 28: rop valid
592  *  - bit 29: beta1 valid
593  *  - bit 30: beta4 valid
594  * word 1:
595  *  - bits 0-1: mono format
596  *  - bits 8-13: color format
597  *  - bits 16-31: DMA_NOTIFY instance
598  * word 2:
599  *  - bits 0-15: DMA_A instance
600  *  - bits 16-31: DMA_B instance
601  *
602  * NV05 will set/unset the relevant valid bits when you poke the relevant
603  * object-binding methods with object of the proper type, or with the NULL
604  * type. It'll only allow rendering using the grobj if all needed objects
605  * are bound. The needed set of objects depends on selected operation: for
606  * example rop object is needed by ROP_AND, but not by SRCCOPY_AND.
607  *
608  * NV04 doesn't have these methods implemented at all, and doesn't have the
609  * relevant bits in grobj. Instead, it'll allow rendering whenever bit 24
610  * is set. So we have to emulate them in software, internally keeping the
611  * same bits as NV05 does. Since grobjs are aligned to 16 bytes on nv04,
612  * but the last word isn't actually used for anything, we abuse it for this
613  * purpose.
614  *
615  * Actually, NV05 can optionally check bit 24 too, but we disable this since
616  * there's no use for it.
617  *
618  * For unknown reasons, NV04 implements surf3d binding in hardware as an
619  * exception. Also for unknown reasons, NV04 doesn't implement the clipping
620  * methods on the surf3d object, so we have to emulate them too.
621  */
622
623 static void
624 nv04_graph_set_ctx1(struct nouveau_channel *chan, uint32_t mask, uint32_t value)
625 {
626         struct drm_device *dev = chan->dev;
627         uint32_t instance = (nv_rd32(dev, NV04_PGRAPH_CTX_SWITCH4) & 0xffff) << 4;
628         int subc = (nv_rd32(dev, NV04_PGRAPH_TRAPPED_ADDR) >> 13) & 0x7;
629         uint32_t tmp;
630
631         tmp  = nv_ri32(dev, instance);
632         tmp &= ~mask;
633         tmp |= value;
634
635         nv_wi32(dev, instance, tmp);
636         nv_wr32(dev, NV04_PGRAPH_CTX_SWITCH1, tmp);
637         nv_wr32(dev, NV04_PGRAPH_CTX_CACHE1 + (subc<<2), tmp);
638 }
639
640 static void
641 nv04_graph_set_ctx_val(struct nouveau_channel *chan, uint32_t mask, uint32_t value)
642 {
643         struct drm_device *dev = chan->dev;
644         uint32_t instance = (nv_rd32(dev, NV04_PGRAPH_CTX_SWITCH4) & 0xffff) << 4;
645         uint32_t tmp, ctx1;
646         int class, op, valid = 1;
647
648         ctx1 = nv_ri32(dev, instance);
649         class = ctx1 & 0xff;
650         op = (ctx1 >> 15) & 7;
651         tmp  = nv_ri32(dev, instance + 0xc);
652         tmp &= ~mask;
653         tmp |= value;
654         nv_wi32(dev, instance + 0xc, tmp);
655
656         /* check for valid surf2d/surf_dst/surf_color */
657         if (!(tmp & 0x02000000))
658                 valid = 0;
659         /* check for valid surf_src/surf_zeta */
660         if ((class == 0x1f || class == 0x48) && !(tmp & 0x04000000))
661                 valid = 0;
662
663         switch (op) {
664         /* SRCCOPY_AND, SRCCOPY: no extra objects required */
665         case 0:
666         case 3:
667                 break;
668         /* ROP_AND: requires pattern and rop */
669         case 1:
670                 if (!(tmp & 0x18000000))
671                         valid = 0;
672                 break;
673         /* BLEND_AND: requires beta1 */
674         case 2:
675                 if (!(tmp & 0x20000000))
676                         valid = 0;
677                 break;
678         /* SRCCOPY_PREMULT, BLEND_PREMULT: beta4 required */
679         case 4:
680         case 5:
681                 if (!(tmp & 0x40000000))
682                         valid = 0;
683                 break;
684         }
685
686         nv04_graph_set_ctx1(chan, 0x01000000, valid << 24);
687 }
688
689 static int
690 nv04_graph_mthd_set_operation(struct nouveau_channel *chan, int grclass,
691                               int mthd, uint32_t data)
692 {
693         if (data > 5)
694                 return 1;
695         /* Old versions of the objects only accept first three operations. */
696         if (data > 2 && grclass < 0x40)
697                 return 1;
698         nv04_graph_set_ctx1(chan, 0x00038000, data << 15);
699         /* changing operation changes set of objects needed for validation */
700         nv04_graph_set_ctx_val(chan, 0, 0);
701         return 0;
702 }
703
704 static int
705 nv04_graph_mthd_surf3d_clip_h(struct nouveau_channel *chan, int grclass,
706                               int mthd, uint32_t data)
707 {
708         uint32_t min = data & 0xffff, max;
709         uint32_t w = data >> 16;
710         if (min & 0x8000)
711                 /* too large */
712                 return 1;
713         if (w & 0x8000)
714                 /* yes, it accepts negative for some reason. */
715                 w |= 0xffff0000;
716         max = min + w;
717         max &= 0x3ffff;
718         nv_wr32(chan->dev, 0x40053c, min);
719         nv_wr32(chan->dev, 0x400544, max);
720         return 0;
721 }
722
723 static int
724 nv04_graph_mthd_surf3d_clip_v(struct nouveau_channel *chan, int grclass,
725                               int mthd, uint32_t data)
726 {
727         uint32_t min = data & 0xffff, max;
728         uint32_t w = data >> 16;
729         if (min & 0x8000)
730                 /* too large */
731                 return 1;
732         if (w & 0x8000)
733                 /* yes, it accepts negative for some reason. */
734                 w |= 0xffff0000;
735         max = min + w;
736         max &= 0x3ffff;
737         nv_wr32(chan->dev, 0x400540, min);
738         nv_wr32(chan->dev, 0x400548, max);
739         return 0;
740 }
741
742 static int
743 nv04_graph_mthd_bind_surf2d(struct nouveau_channel *chan, int grclass,
744                               int mthd, uint32_t data)
745 {
746         switch (nv_ri32(chan->dev, data << 4) & 0xff) {
747         case 0x30:
748                 nv04_graph_set_ctx1(chan, 0x00004000, 0);
749                 nv04_graph_set_ctx_val(chan, 0x02000000, 0);
750                 return 0;
751         case 0x42:
752                 nv04_graph_set_ctx1(chan, 0x00004000, 0);
753                 nv04_graph_set_ctx_val(chan, 0x02000000, 0x02000000);
754                 return 0;
755         }
756         return 1;
757 }
758
759 static int
760 nv04_graph_mthd_bind_surf2d_swzsurf(struct nouveau_channel *chan, int grclass,
761                               int mthd, uint32_t data)
762 {
763         switch (nv_ri32(chan->dev, data << 4) & 0xff) {
764         case 0x30:
765                 nv04_graph_set_ctx1(chan, 0x00004000, 0);
766                 nv04_graph_set_ctx_val(chan, 0x02000000, 0);
767                 return 0;
768         case 0x42:
769                 nv04_graph_set_ctx1(chan, 0x00004000, 0);
770                 nv04_graph_set_ctx_val(chan, 0x02000000, 0x02000000);
771                 return 0;
772         case 0x52:
773                 nv04_graph_set_ctx1(chan, 0x00004000, 0x00004000);
774                 nv04_graph_set_ctx_val(chan, 0x02000000, 0x02000000);
775                 return 0;
776         }
777         return 1;
778 }
779
780 static int
781 nv04_graph_mthd_bind_nv01_patt(struct nouveau_channel *chan, int grclass,
782                               int mthd, uint32_t data)
783 {
784         switch (nv_ri32(chan->dev, data << 4) & 0xff) {
785         case 0x30:
786                 nv04_graph_set_ctx_val(chan, 0x08000000, 0);
787                 return 0;
788         case 0x18:
789                 nv04_graph_set_ctx_val(chan, 0x08000000, 0x08000000);
790                 return 0;
791         }
792         return 1;
793 }
794
795 static int
796 nv04_graph_mthd_bind_nv04_patt(struct nouveau_channel *chan, int grclass,
797                               int mthd, uint32_t data)
798 {
799         switch (nv_ri32(chan->dev, data << 4) & 0xff) {
800         case 0x30:
801                 nv04_graph_set_ctx_val(chan, 0x08000000, 0);
802                 return 0;
803         case 0x44:
804                 nv04_graph_set_ctx_val(chan, 0x08000000, 0x08000000);
805                 return 0;
806         }
807         return 1;
808 }
809
810 static int
811 nv04_graph_mthd_bind_rop(struct nouveau_channel *chan, int grclass,
812                               int mthd, uint32_t data)
813 {
814         switch (nv_ri32(chan->dev, data << 4) & 0xff) {
815         case 0x30:
816                 nv04_graph_set_ctx_val(chan, 0x10000000, 0);
817                 return 0;
818         case 0x43:
819                 nv04_graph_set_ctx_val(chan, 0x10000000, 0x10000000);
820                 return 0;
821         }
822         return 1;
823 }
824
825 static int
826 nv04_graph_mthd_bind_beta1(struct nouveau_channel *chan, int grclass,
827                               int mthd, uint32_t data)
828 {
829         switch (nv_ri32(chan->dev, data << 4) & 0xff) {
830         case 0x30:
831                 nv04_graph_set_ctx_val(chan, 0x20000000, 0);
832                 return 0;
833         case 0x12:
834                 nv04_graph_set_ctx_val(chan, 0x20000000, 0x20000000);
835                 return 0;
836         }
837         return 1;
838 }
839
840 static int
841 nv04_graph_mthd_bind_beta4(struct nouveau_channel *chan, int grclass,
842                               int mthd, uint32_t data)
843 {
844         switch (nv_ri32(chan->dev, data << 4) & 0xff) {
845         case 0x30:
846                 nv04_graph_set_ctx_val(chan, 0x40000000, 0);
847                 return 0;
848         case 0x72:
849                 nv04_graph_set_ctx_val(chan, 0x40000000, 0x40000000);
850                 return 0;
851         }
852         return 1;
853 }
854
855 static int
856 nv04_graph_mthd_bind_surf_dst(struct nouveau_channel *chan, int grclass,
857                               int mthd, uint32_t data)
858 {
859         switch (nv_ri32(chan->dev, data << 4) & 0xff) {
860         case 0x30:
861                 nv04_graph_set_ctx_val(chan, 0x02000000, 0);
862                 return 0;
863         case 0x58:
864                 nv04_graph_set_ctx_val(chan, 0x02000000, 0x02000000);
865                 return 0;
866         }
867         return 1;
868 }
869
870 static int
871 nv04_graph_mthd_bind_surf_src(struct nouveau_channel *chan, int grclass,
872                               int mthd, uint32_t data)
873 {
874         switch (nv_ri32(chan->dev, data << 4) & 0xff) {
875         case 0x30:
876                 nv04_graph_set_ctx_val(chan, 0x04000000, 0);
877                 return 0;
878         case 0x59:
879                 nv04_graph_set_ctx_val(chan, 0x04000000, 0x04000000);
880                 return 0;
881         }
882         return 1;
883 }
884
885 static int
886 nv04_graph_mthd_bind_surf_color(struct nouveau_channel *chan, int grclass,
887                               int mthd, uint32_t data)
888 {
889         switch (nv_ri32(chan->dev, data << 4) & 0xff) {
890         case 0x30:
891                 nv04_graph_set_ctx_val(chan, 0x02000000, 0);
892                 return 0;
893         case 0x5a:
894                 nv04_graph_set_ctx_val(chan, 0x02000000, 0x02000000);
895                 return 0;
896         }
897         return 1;
898 }
899
900 static int
901 nv04_graph_mthd_bind_surf_zeta(struct nouveau_channel *chan, int grclass,
902                               int mthd, uint32_t data)
903 {
904         switch (nv_ri32(chan->dev, data << 4) & 0xff) {
905         case 0x30:
906                 nv04_graph_set_ctx_val(chan, 0x04000000, 0);
907                 return 0;
908         case 0x5b:
909                 nv04_graph_set_ctx_val(chan, 0x04000000, 0x04000000);
910                 return 0;
911         }
912         return 1;
913 }
914
915 static int
916 nv04_graph_mthd_bind_clip(struct nouveau_channel *chan, int grclass,
917                               int mthd, uint32_t data)
918 {
919         switch (nv_ri32(chan->dev, data << 4) & 0xff) {
920         case 0x30:
921                 nv04_graph_set_ctx1(chan, 0x2000, 0);
922                 return 0;
923         case 0x19:
924                 nv04_graph_set_ctx1(chan, 0x2000, 0x2000);
925                 return 0;
926         }
927         return 1;
928 }
929
930 static int
931 nv04_graph_mthd_bind_chroma(struct nouveau_channel *chan, int grclass,
932                               int mthd, uint32_t data)
933 {
934         switch (nv_ri32(chan->dev, data << 4) & 0xff) {
935         case 0x30:
936                 nv04_graph_set_ctx1(chan, 0x1000, 0);
937                 return 0;
938         /* Yes, for some reason even the old versions of objects
939          * accept 0x57 and not 0x17. Consistency be damned.
940          */
941         case 0x57:
942                 nv04_graph_set_ctx1(chan, 0x1000, 0x1000);
943                 return 0;
944         }
945         return 1;
946 }
947
948 static struct nouveau_pgraph_object_method nv04_graph_mthds_sw[] = {
949         { 0x0150, nv04_graph_mthd_set_ref },
950         {}
951 };
952
953 static struct nouveau_pgraph_object_method nv04_graph_mthds_nv03_gdirect[] = {
954         { 0x0184, nv04_graph_mthd_bind_nv01_patt },
955         { 0x0188, nv04_graph_mthd_bind_rop },
956         { 0x018c, nv04_graph_mthd_bind_beta1 },
957         { 0x0190, nv04_graph_mthd_bind_surf_dst },
958         { 0x02fc, nv04_graph_mthd_set_operation },
959         {},
960 };
961
962 static struct nouveau_pgraph_object_method nv04_graph_mthds_nv04_gdirect[] = {
963         { 0x0188, nv04_graph_mthd_bind_nv04_patt },
964         { 0x018c, nv04_graph_mthd_bind_rop },
965         { 0x0190, nv04_graph_mthd_bind_beta1 },
966         { 0x0194, nv04_graph_mthd_bind_beta4 },
967         { 0x0198, nv04_graph_mthd_bind_surf2d },
968         { 0x02fc, nv04_graph_mthd_set_operation },
969         {},
970 };
971
972 static struct nouveau_pgraph_object_method nv04_graph_mthds_nv01_imageblit[] = {
973         { 0x0184, nv04_graph_mthd_bind_chroma },
974         { 0x0188, nv04_graph_mthd_bind_clip },
975         { 0x018c, nv04_graph_mthd_bind_nv01_patt },
976         { 0x0190, nv04_graph_mthd_bind_rop },
977         { 0x0194, nv04_graph_mthd_bind_beta1 },
978         { 0x0198, nv04_graph_mthd_bind_surf_dst },
979         { 0x019c, nv04_graph_mthd_bind_surf_src },
980         { 0x02fc, nv04_graph_mthd_set_operation },
981         {},
982 };
983
984 static struct nouveau_pgraph_object_method nv04_graph_mthds_nv04_imageblit_ifc[] = {
985         { 0x0184, nv04_graph_mthd_bind_chroma },
986         { 0x0188, nv04_graph_mthd_bind_clip },
987         { 0x018c, nv04_graph_mthd_bind_nv04_patt },
988         { 0x0190, nv04_graph_mthd_bind_rop },
989         { 0x0194, nv04_graph_mthd_bind_beta1 },
990         { 0x0198, nv04_graph_mthd_bind_beta4 },
991         { 0x019c, nv04_graph_mthd_bind_surf2d },
992         { 0x02fc, nv04_graph_mthd_set_operation },
993         {},
994 };
995
996 static struct nouveau_pgraph_object_method nv04_graph_mthds_nv04_iifc[] = {
997         { 0x0188, nv04_graph_mthd_bind_chroma },
998         { 0x018c, nv04_graph_mthd_bind_clip },
999         { 0x0190, nv04_graph_mthd_bind_nv04_patt },
1000         { 0x0194, nv04_graph_mthd_bind_rop },
1001         { 0x0198, nv04_graph_mthd_bind_beta1 },
1002         { 0x019c, nv04_graph_mthd_bind_beta4 },
1003         { 0x01a0, nv04_graph_mthd_bind_surf2d_swzsurf },
1004         { 0x03e4, nv04_graph_mthd_set_operation },
1005         {},
1006 };
1007
1008 static struct nouveau_pgraph_object_method nv04_graph_mthds_nv01_ifc[] = {
1009         { 0x0184, nv04_graph_mthd_bind_chroma },
1010         { 0x0188, nv04_graph_mthd_bind_clip },
1011         { 0x018c, nv04_graph_mthd_bind_nv01_patt },
1012         { 0x0190, nv04_graph_mthd_bind_rop },
1013         { 0x0194, nv04_graph_mthd_bind_beta1 },
1014         { 0x0198, nv04_graph_mthd_bind_surf_dst },
1015         { 0x02fc, nv04_graph_mthd_set_operation },
1016         {},
1017 };
1018
1019 static struct nouveau_pgraph_object_method nv04_graph_mthds_nv03_sifc[] = {
1020         { 0x0184, nv04_graph_mthd_bind_chroma },
1021         { 0x0188, nv04_graph_mthd_bind_nv01_patt },
1022         { 0x018c, nv04_graph_mthd_bind_rop },
1023         { 0x0190, nv04_graph_mthd_bind_beta1 },
1024         { 0x0194, nv04_graph_mthd_bind_surf_dst },
1025         { 0x02fc, nv04_graph_mthd_set_operation },
1026         {},
1027 };
1028
1029 static struct nouveau_pgraph_object_method nv04_graph_mthds_nv04_sifc[] = {
1030         { 0x0184, nv04_graph_mthd_bind_chroma },
1031         { 0x0188, nv04_graph_mthd_bind_nv04_patt },
1032         { 0x018c, nv04_graph_mthd_bind_rop },
1033         { 0x0190, nv04_graph_mthd_bind_beta1 },
1034         { 0x0194, nv04_graph_mthd_bind_beta4 },
1035         { 0x0198, nv04_graph_mthd_bind_surf2d },
1036         { 0x02fc, nv04_graph_mthd_set_operation },
1037         {},
1038 };
1039
1040 static struct nouveau_pgraph_object_method nv04_graph_mthds_nv03_sifm[] = {
1041         { 0x0188, nv04_graph_mthd_bind_nv01_patt },
1042         { 0x018c, nv04_graph_mthd_bind_rop },
1043         { 0x0190, nv04_graph_mthd_bind_beta1 },
1044         { 0x0194, nv04_graph_mthd_bind_surf_dst },
1045         { 0x0304, nv04_graph_mthd_set_operation },
1046         {},
1047 };
1048
1049 static struct nouveau_pgraph_object_method nv04_graph_mthds_nv04_sifm[] = {
1050         { 0x0188, nv04_graph_mthd_bind_nv04_patt },
1051         { 0x018c, nv04_graph_mthd_bind_rop },
1052         { 0x0190, nv04_graph_mthd_bind_beta1 },
1053         { 0x0194, nv04_graph_mthd_bind_beta4 },
1054         { 0x0198, nv04_graph_mthd_bind_surf2d_swzsurf },
1055         { 0x0304, nv04_graph_mthd_set_operation },
1056         {},
1057 };
1058
1059 static struct nouveau_pgraph_object_method nv04_graph_mthds_nv01_shape[] = {
1060         { 0x0184, nv04_graph_mthd_bind_clip },
1061         { 0x0188, nv04_graph_mthd_bind_nv01_patt },
1062         { 0x018c, nv04_graph_mthd_bind_rop },
1063         { 0x0190, nv04_graph_mthd_bind_beta1 },
1064         { 0x0194, nv04_graph_mthd_bind_surf_dst },
1065         { 0x02fc, nv04_graph_mthd_set_operation },
1066         {},
1067 };
1068
1069 static struct nouveau_pgraph_object_method nv04_graph_mthds_nv04_shape[] = {
1070         { 0x0184, nv04_graph_mthd_bind_clip },
1071         { 0x0188, nv04_graph_mthd_bind_nv04_patt },
1072         { 0x018c, nv04_graph_mthd_bind_rop },
1073         { 0x0190, nv04_graph_mthd_bind_beta1 },
1074         { 0x0194, nv04_graph_mthd_bind_beta4 },
1075         { 0x0198, nv04_graph_mthd_bind_surf2d },
1076         { 0x02fc, nv04_graph_mthd_set_operation },
1077         {},
1078 };
1079
1080 static struct nouveau_pgraph_object_method nv04_graph_mthds_nv03_tex_tri[] = {
1081         { 0x0188, nv04_graph_mthd_bind_clip },
1082         { 0x018c, nv04_graph_mthd_bind_surf_color },
1083         { 0x0190, nv04_graph_mthd_bind_surf_zeta },
1084         {},
1085 };
1086
1087 static struct nouveau_pgraph_object_method nv04_graph_mthds_surf3d[] = {
1088         { 0x02f8, nv04_graph_mthd_surf3d_clip_h },
1089         { 0x02fc, nv04_graph_mthd_surf3d_clip_v },
1090         {},
1091 };
1092
1093 struct nouveau_pgraph_object_class nv04_graph_grclass[] = {
1094         { 0x0038, NVOBJ_ENGINE_GR, NULL }, /* dvd subpicture */
1095         { 0x0039, NVOBJ_ENGINE_GR, NULL }, /* m2mf */
1096         { 0x004b, NVOBJ_ENGINE_GR, nv04_graph_mthds_nv03_gdirect }, /* nv03 gdirect */
1097         { 0x004a, NVOBJ_ENGINE_GR, nv04_graph_mthds_nv04_gdirect }, /* nv04 gdirect */
1098         { 0x001f, NVOBJ_ENGINE_GR, nv04_graph_mthds_nv01_imageblit }, /* nv01 imageblit */
1099         { 0x005f, NVOBJ_ENGINE_GR, nv04_graph_mthds_nv04_imageblit_ifc }, /* nv04 imageblit */
1100         { 0x0060, NVOBJ_ENGINE_GR, nv04_graph_mthds_nv04_iifc }, /* nv04 iifc */
1101         { 0x0064, NVOBJ_ENGINE_GR, NULL }, /* nv05 iifc */
1102         { 0x0021, NVOBJ_ENGINE_GR, nv04_graph_mthds_nv01_ifc }, /* nv01 ifc */
1103         { 0x0061, NVOBJ_ENGINE_GR, nv04_graph_mthds_nv04_imageblit_ifc }, /* nv04 ifc */
1104         { 0x0065, NVOBJ_ENGINE_GR, NULL }, /* nv05 ifc */
1105         { 0x0036, NVOBJ_ENGINE_GR, nv04_graph_mthds_nv03_sifc }, /* nv03 sifc */
1106         { 0x0076, NVOBJ_ENGINE_GR, nv04_graph_mthds_nv04_sifc }, /* nv04 sifc */
1107         { 0x0066, NVOBJ_ENGINE_GR, NULL }, /* nv05 sifc */
1108         { 0x0037, NVOBJ_ENGINE_GR, nv04_graph_mthds_nv03_sifm }, /* nv03 sifm */
1109         { 0x0077, NVOBJ_ENGINE_GR, nv04_graph_mthds_nv04_sifm }, /* nv04 sifm */
1110         { 0x0030, NVOBJ_ENGINE_GR, NULL }, /* null */
1111         { 0x0042, NVOBJ_ENGINE_GR, NULL }, /* surf2d */
1112         { 0x0043, NVOBJ_ENGINE_GR, NULL }, /* rop */
1113         { 0x0012, NVOBJ_ENGINE_GR, NULL }, /* beta1 */
1114         { 0x0072, NVOBJ_ENGINE_GR, NULL }, /* beta4 */
1115         { 0x0019, NVOBJ_ENGINE_GR, NULL }, /* cliprect */
1116         { 0x0018, NVOBJ_ENGINE_GR, NULL }, /* nv01 pattern */
1117         { 0x0044, NVOBJ_ENGINE_GR, NULL }, /* nv04 pattern */
1118         { 0x0052, NVOBJ_ENGINE_GR, NULL }, /* swzsurf */
1119         { 0x0053, NVOBJ_ENGINE_GR, nv04_graph_mthds_surf3d }, /* surf3d */
1120         { 0x0048, NVOBJ_ENGINE_GR, nv04_graph_mthds_nv03_tex_tri }, /* nv03 tex_tri */
1121         { 0x0054, NVOBJ_ENGINE_GR, NULL }, /* tex_tri */
1122         { 0x0055, NVOBJ_ENGINE_GR, NULL }, /* multitex_tri */
1123         { 0x0017, NVOBJ_ENGINE_GR, NULL }, /* nv01 chroma */
1124         { 0x0057, NVOBJ_ENGINE_GR, NULL }, /* nv04 chroma */
1125         { 0x0058, NVOBJ_ENGINE_GR, NULL }, /* surf_dst */
1126         { 0x0059, NVOBJ_ENGINE_GR, NULL }, /* surf_src */
1127         { 0x005a, NVOBJ_ENGINE_GR, NULL }, /* surf_color */
1128         { 0x005b, NVOBJ_ENGINE_GR, NULL }, /* surf_zeta */
1129         { 0x001c, NVOBJ_ENGINE_GR, nv04_graph_mthds_nv01_shape }, /* nv01 line */
1130         { 0x005c, NVOBJ_ENGINE_GR, nv04_graph_mthds_nv04_shape }, /* nv04 line */
1131         { 0x001d, NVOBJ_ENGINE_GR, nv04_graph_mthds_nv01_shape }, /* nv01 tri */
1132         { 0x005d, NVOBJ_ENGINE_GR, nv04_graph_mthds_nv04_shape }, /* nv04 tri */
1133         { 0x001e, NVOBJ_ENGINE_GR, nv04_graph_mthds_nv01_shape }, /* nv01 rect */
1134         { 0x005e, NVOBJ_ENGINE_GR, nv04_graph_mthds_nv04_shape }, /* nv04 rect */
1135         { 0x506e, NVOBJ_ENGINE_SW, nv04_graph_mthds_sw },
1136         {}
1137 };
1138