2 * Copyright 2007 Ben Skeggs
4 * Permission is hereby granted, free of charge, to any person obtaining a
5 * copy of this software and associated documentation files (the "Software"),
6 * to deal in the Software without restriction, including without limitation
7 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
8 * and/or sell copies of the Software, and to permit persons to whom the
9 * Software is furnished to do so, subject to the following conditions:
11 * The above copyright notice and this permission notice shall be included in
12 * all copies or substantial portions of the Software.
14 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
16 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
17 * THE AUTHORS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
18 * WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF
19 * OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
23 #include "nv_include.h"
26 NVAccelInitNullObject(ScrnInfoPtr pScrn)
28 NVPtr pNv = NVPTR(pScrn);
31 if (nouveau_grobj_alloc(pNv->chan, NvNullObject, NV01_NULL,
40 NVAccelInitDmaNotifier0(ScrnInfoPtr pScrn)
42 NVPtr pNv = NVPTR(pScrn);
45 if (nouveau_notifier_alloc(pNv->chan, NvDmaNotifier0, 1,
53 /* FLAGS_ROP_AND, DmaFB, DmaFB, 0 */
55 NVAccelInitContextSurfaces(ScrnInfoPtr pScrn)
57 NVPtr pNv = NVPTR(pScrn);
60 class = (pNv->Architecture >= NV_10) ? NV10_CONTEXT_SURFACES_2D :
61 NV04_CONTEXT_SURFACES_2D;
63 if (!pNv->NvContextSurfaces) {
64 if (nouveau_grobj_alloc(pNv->chan, NvContextSurfaces, class,
65 &pNv->NvContextSurfaces))
69 BEGIN_RING(NvContextSurfaces, NV04_CONTEXT_SURFACES_2D_DMA_NOTIFY, 1);
70 OUT_RING (pNv->NvNull->handle);
71 BEGIN_RING(NvContextSurfaces,
72 NV04_CONTEXT_SURFACES_2D_DMA_IMAGE_SOURCE, 2);
73 OUT_RING (pNv->chan->vram->handle);
74 OUT_RING (pNv->chan->vram->handle);
79 /* FLAGS_ROP_AND, DmaFB, DmaFB, 0 */
81 NVAccelInitContextBeta1(ScrnInfoPtr pScrn)
83 NVPtr pNv = NVPTR(pScrn);
88 if (!pNv->NvContextBeta1) {
89 if (nouveau_grobj_alloc(pNv->chan, NvContextBeta1, class,
90 &pNv->NvContextBeta1))
94 BEGIN_RING(NvContextBeta1, 0x300, 1); /*alpha factor*/
95 OUT_RING (0xff << 23);
102 NVAccelInitContextBeta4(ScrnInfoPtr pScrn)
104 NVPtr pNv = NVPTR(pScrn);
109 if (!pNv->NvContextBeta4) {
110 if (nouveau_grobj_alloc(pNv->chan, NvContextBeta4, class,
111 &pNv->NvContextBeta4))
115 BEGIN_RING(NvContextBeta4, 0x300, 1); /*RGBA factor*/
116 OUT_RING (0xffff0000);
121 NVAccelGetCtxSurf2DFormatFromPixmap(PixmapPtr pPix, int *fmt_ret)
123 switch (pPix->drawable.bitsPerPixel) {
125 *fmt_ret = NV04_CONTEXT_SURFACES_2D_FORMAT_A8R8G8B8;
128 *fmt_ret = NV04_CONTEXT_SURFACES_2D_FORMAT_X8R8G8B8_Z8R8G8B8;
131 *fmt_ret = NV04_CONTEXT_SURFACES_2D_FORMAT_R5G6B5;
134 *fmt_ret = NV04_CONTEXT_SURFACES_2D_FORMAT_Y8;
144 NVAccelGetCtxSurf2DFormatFromPicture(PicturePtr pPict, int *fmt_ret)
146 switch (pPict->format) {
148 *fmt_ret = NV04_CONTEXT_SURFACES_2D_FORMAT_A8R8G8B8;
151 *fmt_ret = NV04_CONTEXT_SURFACES_2D_FORMAT_X8R8G8B8_Z8R8G8B8;
154 *fmt_ret = NV04_CONTEXT_SURFACES_2D_FORMAT_R5G6B5;
157 *fmt_ret = NV04_CONTEXT_SURFACES_2D_FORMAT_Y8;
166 /* A copy of exaGetOffscreenPixmap(), since it's private. */
168 NVGetDrawablePixmap(DrawablePtr pDraw)
170 if (pDraw->type == DRAWABLE_WINDOW)
171 return pDraw->pScreen->GetWindowPixmap ((WindowPtr) pDraw);
173 return (PixmapPtr) pDraw;
177 NVAccelInitImagePattern(ScrnInfoPtr pScrn)
179 NVPtr pNv = NVPTR(pScrn);
182 class = NV04_IMAGE_PATTERN;
184 if (!pNv->NvImagePattern) {
185 if (nouveau_grobj_alloc(pNv->chan, NvImagePattern, class,
186 &pNv->NvImagePattern))
190 BEGIN_RING(NvImagePattern, NV04_IMAGE_PATTERN_DMA_NOTIFY, 1);
191 OUT_RING (pNv->NvNull->handle);
192 BEGIN_RING(NvImagePattern, NV04_IMAGE_PATTERN_MONOCHROME_FORMAT, 3);
193 #if X_BYTE_ORDER == X_BIG_ENDIAN
194 OUT_RING (NV04_IMAGE_PATTERN_MONOCHROME_FORMAT_LE);
196 OUT_RING (NV04_IMAGE_PATTERN_MONOCHROME_FORMAT_CGA6);
198 OUT_RING (NV04_IMAGE_PATTERN_MONOCHROME_SHAPE_8X8);
199 OUT_RING (NV04_IMAGE_PATTERN_PATTERN_SELECT_MONO);
205 NVAccelInitRasterOp(ScrnInfoPtr pScrn)
207 NVPtr pNv = NVPTR(pScrn);
210 class = NV03_CONTEXT_ROP;
213 if (nouveau_grobj_alloc(pNv->chan, NvRop, class,
218 BEGIN_RING(NvRop, NV03_CONTEXT_ROP_DMA_NOTIFY, 1);
219 OUT_RING (pNv->NvNull->handle);
221 pNv->currentRop = ~0;
226 NVAccelInitRectangle(ScrnInfoPtr pScrn)
228 NVPtr pNv = NVPTR(pScrn);
231 class = NV04_GDI_RECTANGLE_TEXT;
233 if (!pNv->NvRectangle) {
234 if (nouveau_grobj_alloc(pNv->chan, NvRectangle, class,
239 BEGIN_RING(NvRectangle, NV04_GDI_RECTANGLE_TEXT_DMA_NOTIFY, 1);
240 OUT_RING (pNv->notify0->handle);
241 BEGIN_RING(NvRectangle, NV04_GDI_RECTANGLE_TEXT_DMA_FONTS, 1);
242 OUT_RING (pNv->NvNull->handle);
243 BEGIN_RING(NvRectangle, NV04_GDI_RECTANGLE_TEXT_SURFACE, 1);
244 OUT_RING (pNv->NvContextSurfaces->handle);
245 BEGIN_RING(NvRectangle, NV04_GDI_RECTANGLE_TEXT_ROP, 1);
246 OUT_RING (pNv->NvRop->handle);
247 BEGIN_RING(NvRectangle, NV04_GDI_RECTANGLE_TEXT_PATTERN, 1);
248 OUT_RING (pNv->NvImagePattern->handle);
249 BEGIN_RING(NvRectangle, NV04_GDI_RECTANGLE_TEXT_OPERATION, 1);
250 OUT_RING (NV04_GDI_RECTANGLE_TEXT_OPERATION_ROP_AND);
251 BEGIN_RING(NvRectangle, NV04_GDI_RECTANGLE_TEXT_MONOCHROME_FORMAT, 1);
252 /* XXX why putting 1 like renouveau dump, swap the text */
253 #if 1 || X_BYTE_ORDER == X_BIG_ENDIAN
254 OUT_RING (NV04_GDI_RECTANGLE_TEXT_MONOCHROME_FORMAT_LE);
256 OUT_RING (NV04_GDI_RECTANGLE_TEXT_MONOCHROME_FORMAT_CGA6);
263 NVAccelInitImageBlit(ScrnInfoPtr pScrn)
265 NVPtr pNv = NVPTR(pScrn);
268 class = (pNv->WaitVSyncPossible) ? NV12_IMAGE_BLIT : NV04_IMAGE_BLIT;
270 if (!pNv->NvImageBlit) {
271 if (nouveau_grobj_alloc(pNv->chan, NvImageBlit, class,
276 BEGIN_RING(NvImageBlit, NV04_IMAGE_BLIT_DMA_NOTIFY, 1);
277 OUT_RING (pNv->notify0->handle);
278 BEGIN_RING(NvImageBlit, NV04_IMAGE_BLIT_COLOR_KEY, 1);
279 OUT_RING (pNv->NvNull->handle);
280 BEGIN_RING(NvImageBlit, NV04_IMAGE_BLIT_SURFACE, 1);
281 OUT_RING (pNv->NvContextSurfaces->handle);
282 BEGIN_RING(NvImageBlit, NV04_IMAGE_BLIT_CLIP_RECTANGLE, 3);
283 OUT_RING (pNv->NvNull->handle);
284 OUT_RING (pNv->NvImagePattern->handle);
285 OUT_RING (pNv->NvRop->handle);
286 BEGIN_RING(NvImageBlit, NV04_IMAGE_BLIT_OPERATION, 1);
287 OUT_RING (NV04_IMAGE_BLIT_OPERATION_ROP_AND);
289 if (pNv->WaitVSyncPossible) {
290 BEGIN_RING(NvImageBlit, 0x0120, 3);
300 NVAccelInitScaledImage(ScrnInfoPtr pScrn)
302 NVPtr pNv = NVPTR(pScrn);
305 switch (pNv->Architecture) {
307 class = NV04_SCALED_IMAGE_FROM_MEMORY;
312 class = NV10_SCALED_IMAGE_FROM_MEMORY;
316 class = NV10_SCALED_IMAGE_FROM_MEMORY | 0x3000;
320 if (!pNv->NvScaledImage) {
321 if (nouveau_grobj_alloc(pNv->chan, NvScaledImage, class,
322 &pNv->NvScaledImage))
326 BEGIN_RING(NvScaledImage,
327 NV04_SCALED_IMAGE_FROM_MEMORY_DMA_NOTIFY, 7);
328 OUT_RING (pNv->notify0->handle);
329 OUT_RING (pNv->chan->vram->handle);
330 OUT_RING (pNv->NvNull->handle);
331 OUT_RING (pNv->NvNull->handle);
332 OUT_RING (pNv->NvContextBeta1->handle);
333 OUT_RING (pNv->NvContextBeta4->handle);
334 OUT_RING (pNv->NvContextSurfaces->handle);
335 if (pNv->Architecture>=NV_ARCH_10) {
336 BEGIN_RING(NvScaledImage,
337 NV04_SCALED_IMAGE_FROM_MEMORY_COLOR_CONVERSION, 1);
338 OUT_RING (NV04_SCALED_IMAGE_FROM_MEMORY_COLOR_CONVERSION_DITHER);
340 BEGIN_RING(NvScaledImage, NV04_SCALED_IMAGE_FROM_MEMORY_OPERATION, 1);
341 OUT_RING (NV04_SCALED_IMAGE_FROM_MEMORY_OPERATION_SRCCOPY);
347 NVAccelInitClipRectangle(ScrnInfoPtr pScrn)
349 NVPtr pNv = NVPTR(pScrn);
350 int class = NV01_CONTEXT_CLIP_RECTANGLE;
352 if (!pNv->NvClipRectangle) {
353 if (nouveau_grobj_alloc(pNv->chan, NvClipRectangle, class,
354 &pNv->NvClipRectangle))
358 BEGIN_RING(NvClipRectangle, NV01_CONTEXT_CLIP_RECTANGLE_DMA_NOTIFY, 1);
359 OUT_RING (pNv->NvNull->handle);
364 /* FLAGS_NONE, NvDmaFB, NvDmaAGP, NvDmaNotifier0 */
366 NVAccelInitMemFormat(ScrnInfoPtr pScrn)
368 NVPtr pNv = NVPTR(pScrn);
371 if (pNv->Architecture < NV_ARCH_50)
372 class = NV04_MEMORY_TO_MEMORY_FORMAT;
374 class = NV50_MEMORY_TO_MEMORY_FORMAT;
376 if (!pNv->NvMemFormat) {
377 if (nouveau_grobj_alloc(pNv->chan, NvMemFormat, class,
382 BEGIN_RING(NvMemFormat, NV04_MEMORY_TO_MEMORY_FORMAT_DMA_NOTIFY, 1);
383 OUT_RING (pNv->notify0->handle);
384 BEGIN_RING(NvMemFormat, NV04_MEMORY_TO_MEMORY_FORMAT_DMA_BUFFER_IN, 2);
385 OUT_RING (pNv->chan->vram->handle);
386 OUT_RING (pNv->chan->vram->handle);
392 NVAccelInitImageFromCpu(ScrnInfoPtr pScrn)
394 NVPtr pNv = NVPTR(pScrn);
397 switch (pNv->Architecture) {
399 class = NV04_IMAGE_FROM_CPU;
406 class = NV10_IMAGE_FROM_CPU;
410 if (!pNv->NvImageFromCpu) {
411 if (nouveau_grobj_alloc(pNv->chan, NvImageFromCpu, class,
412 &pNv->NvImageFromCpu))
416 BEGIN_RING(NvImageFromCpu, NV01_IMAGE_FROM_CPU_DMA_NOTIFY, 1);
417 OUT_RING (pNv->notify0->handle);
418 BEGIN_RING(NvImageFromCpu, NV01_IMAGE_FROM_CPU_CLIP_RECTANGLE, 1);
419 OUT_RING (pNv->NvNull->handle);
420 BEGIN_RING(NvImageFromCpu, NV01_IMAGE_FROM_CPU_PATTERN, 1);
421 OUT_RING (pNv->NvNull->handle);
422 BEGIN_RING(NvImageFromCpu, NV01_IMAGE_FROM_CPU_ROP, 1);
423 OUT_RING (pNv->NvNull->handle);
424 if (pNv->Architecture >= NV_ARCH_10)
426 BEGIN_RING(NvImageFromCpu, NV01_IMAGE_FROM_CPU_BETA1, 1);
427 OUT_RING (pNv->NvNull->handle);
428 BEGIN_RING(NvImageFromCpu, NV05_IMAGE_FROM_CPU_BETA4, 1);
429 OUT_RING (pNv->NvNull->handle);
431 BEGIN_RING(NvImageFromCpu, NV05_IMAGE_FROM_CPU_SURFACE, 1);
432 OUT_RING (pNv->NvContextSurfaces->handle);
433 BEGIN_RING(NvImageFromCpu, NV01_IMAGE_FROM_CPU_OPERATION, 1);
434 OUT_RING (NV01_IMAGE_FROM_CPU_OPERATION_SRCCOPY);
439 NVAccelInit2D_NV50(ScrnInfoPtr pScrn)
441 NVPtr pNv = NVPTR(pScrn);
444 if (nouveau_grobj_alloc(pNv->chan, Nv2D, 0x502d,
449 BEGIN_RING(Nv2D, 0x180, 3);
450 OUT_RING (pNv->notify0->handle);
451 OUT_RING (pNv->chan->vram->handle);
452 OUT_RING (pNv->chan->vram->handle);
454 /* Magics from nv, no clue what they do, but at least some
455 * of them are needed to avoid crashes.
457 BEGIN_RING(Nv2D, 0x260, 1);
459 BEGIN_RING(Nv2D, 0x290, 1);
461 BEGIN_RING(Nv2D, 0x29c, 1);
463 BEGIN_RING(Nv2D, 0x58c, 1);
466 pNv->currentRop = 0xfffffffa;
470 #define INIT_CONTEXT_OBJECT(name) do { \
471 ret = NVAccelInit##name(pScrn); \
473 xf86DrvMsg(pScrn->scrnIndex, X_ERROR, \
474 "Failed to initialise context object: "#name \
481 NVAccelCommonInit(ScrnInfoPtr pScrn)
483 NVPtr pNv = NVPTR(pScrn);
485 if(pNv->NoAccel) return TRUE;
487 /* General engine objects */
488 INIT_CONTEXT_OBJECT(NullObject);
489 INIT_CONTEXT_OBJECT(DmaNotifier0);
492 if (pNv->Architecture < NV_ARCH_50) {
493 INIT_CONTEXT_OBJECT(ContextSurfaces);
494 INIT_CONTEXT_OBJECT(ContextBeta1);
495 INIT_CONTEXT_OBJECT(ContextBeta4);
496 INIT_CONTEXT_OBJECT(ImagePattern);
497 INIT_CONTEXT_OBJECT(RasterOp);
498 INIT_CONTEXT_OBJECT(Rectangle);
499 INIT_CONTEXT_OBJECT(ImageBlit);
500 INIT_CONTEXT_OBJECT(ScaledImage);
501 INIT_CONTEXT_OBJECT(ClipRectangle);
502 INIT_CONTEXT_OBJECT(ImageFromCpu);
504 INIT_CONTEXT_OBJECT(2D_NV50);
506 INIT_CONTEXT_OBJECT(MemFormat);
509 switch (pNv->Architecture) {
511 INIT_CONTEXT_OBJECT(NV40TCL);
514 INIT_CONTEXT_OBJECT(NV30TCL);
518 INIT_CONTEXT_OBJECT(NV10TCL);