i915_video.c revision 13496ba1
103b705cfSriastradh/* 203b705cfSriastradh * Copyright © 2006 Intel Corporation 303b705cfSriastradh * 403b705cfSriastradh * Permission is hereby granted, free of charge, to any person obtaining a 503b705cfSriastradh * copy of this software and associated documentation files (the "Software"), 603b705cfSriastradh * to deal in the Software without restriction, including without limitation 703b705cfSriastradh * the rights to use, copy, modify, merge, publish, distribute, sublicense, 803b705cfSriastradh * and/or sell copies of the Software, and to permit persons to whom the 903b705cfSriastradh * Software is furnished to do so, subject to the following conditions: 1003b705cfSriastradh * 1103b705cfSriastradh * The above copyright notice and this permission notice (including the next 1203b705cfSriastradh * paragraph) shall be included in all copies or substantial portions of the 1303b705cfSriastradh * Software. 1403b705cfSriastradh * 1503b705cfSriastradh * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 1603b705cfSriastradh * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 1703b705cfSriastradh * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL 1803b705cfSriastradh * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 1903b705cfSriastradh * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 2003b705cfSriastradh * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 2103b705cfSriastradh * SOFTWARE. 2203b705cfSriastradh * 2303b705cfSriastradh * Authors: 2403b705cfSriastradh * Eric Anholt <eric@anholt.net> 2503b705cfSriastradh * 2603b705cfSriastradh */ 2703b705cfSriastradh 2803b705cfSriastradh#ifdef HAVE_CONFIG_H 2903b705cfSriastradh#include "config.h" 3003b705cfSriastradh#endif 3103b705cfSriastradh 3242542f5fSchristos#include "xorg-server.h" 3303b705cfSriastradh#include "xf86.h" 3403b705cfSriastradh#include "xf86_OSproc.h" 3503b705cfSriastradh#include "xf86xv.h" 3603b705cfSriastradh#include "fourcc.h" 3703b705cfSriastradh#include "gcstruct.h" 3803b705cfSriastradh 3903b705cfSriastradh#include "intel.h" 4013496ba1Ssnj#include "intel_uxa.h" 4103b705cfSriastradh#include "i915_reg.h" 4203b705cfSriastradh#include "i915_3d.h" 4303b705cfSriastradh 4403b705cfSriastradhvoid 4503b705cfSriastradhI915DisplayVideoTextured(ScrnInfoPtr scrn, 4603b705cfSriastradh intel_adaptor_private *adaptor_priv, int id, 4703b705cfSriastradh RegionPtr dstRegion, 4803b705cfSriastradh short width, short height, int video_pitch, 4903b705cfSriastradh int video_pitch2, 5003b705cfSriastradh short src_w, short src_h, short drw_w, short drw_h, 5103b705cfSriastradh PixmapPtr pixmap) 5203b705cfSriastradh{ 5303b705cfSriastradh intel_screen_private *intel = intel_get_screen_private(scrn); 5403b705cfSriastradh uint32_t format, ms3, s5, tiling; 5503b705cfSriastradh BoxPtr pbox = REGION_RECTS(dstRegion); 5603b705cfSriastradh int nbox_total = REGION_NUM_RECTS(dstRegion); 5703b705cfSriastradh int nbox_this_time; 5803b705cfSriastradh int dxo, dyo, pix_xoff, pix_yoff; 5903b705cfSriastradh PixmapPtr target; 6003b705cfSriastradh 6103b705cfSriastradh#if 0 6203b705cfSriastradh ErrorF("I915DisplayVideo: %dx%d (pitch %d)\n", width, height, 6303b705cfSriastradh video_pitch); 6403b705cfSriastradh#endif 6503b705cfSriastradh 6603b705cfSriastradh dxo = dstRegion->extents.x1; 6703b705cfSriastradh dyo = dstRegion->extents.y1; 6803b705cfSriastradh 6903b705cfSriastradh if (pixmap->drawable.width > 2048 || pixmap->drawable.height > 2048 || 7013496ba1Ssnj !intel_uxa_check_pitch_3d(pixmap)) { 7103b705cfSriastradh ScreenPtr screen = pixmap->drawable.pScreen; 7203b705cfSriastradh 7303b705cfSriastradh target = screen->CreatePixmap(screen, 7403b705cfSriastradh dstRegion->extents.x2 - dxo, 7503b705cfSriastradh dstRegion->extents.y2 - dyo, 7603b705cfSriastradh pixmap->drawable.depth, 7703b705cfSriastradh CREATE_PIXMAP_USAGE_SCRATCH); 7803b705cfSriastradh if (target == NULL) 7903b705cfSriastradh return; 8003b705cfSriastradh 8113496ba1Ssnj if (intel_uxa_get_pixmap_bo(target) == NULL) { 8242542f5fSchristos screen->DestroyPixmap(target); 8342542f5fSchristos return; 8442542f5fSchristos } 8542542f5fSchristos 8603b705cfSriastradh pix_xoff = -dxo; 8703b705cfSriastradh pix_yoff = -dyo; 8803b705cfSriastradh } else { 8903b705cfSriastradh target = pixmap; 9003b705cfSriastradh 9103b705cfSriastradh /* Set up the offset for translating from the given region 9203b705cfSriastradh * (in screen coordinates) to the backing pixmap. 9303b705cfSriastradh */ 9403b705cfSriastradh#ifdef COMPOSITE 9503b705cfSriastradh pix_xoff = -target->screen_x + target->drawable.x; 9603b705cfSriastradh pix_yoff = -target->screen_y + target->drawable.y; 9703b705cfSriastradh#else 9803b705cfSriastradh pix_xoff = 0; 9903b705cfSriastradh pix_yoff = 0; 10003b705cfSriastradh#endif 10103b705cfSriastradh } 10203b705cfSriastradh 10303b705cfSriastradh#define BYTES_FOR_BOXES(n) ((200 + (n) * 20) * 4) 10403b705cfSriastradh#define BOXES_IN_BYTES(s) ((((s)/4) - 200) / 20) 10503b705cfSriastradh#define BATCH_BYTES(p) ((p)->batch_bo->size - 16) 10603b705cfSriastradh 10703b705cfSriastradh while (nbox_total) { 10803b705cfSriastradh nbox_this_time = nbox_total; 10903b705cfSriastradh if (BYTES_FOR_BOXES(nbox_this_time) > BATCH_BYTES(intel)) 11003b705cfSriastradh nbox_this_time = BOXES_IN_BYTES(BATCH_BYTES(intel)); 11103b705cfSriastradh nbox_total -= nbox_this_time; 11203b705cfSriastradh 11303b705cfSriastradh intel_batch_start_atomic(scrn, 200 + 20 * nbox_this_time); 11403b705cfSriastradh 11503b705cfSriastradh IntelEmitInvarientState(scrn); 11603b705cfSriastradh intel->last_3d = LAST_3D_VIDEO; 11703b705cfSriastradh 11803b705cfSriastradh /* draw rect -- just clipping */ 11903b705cfSriastradh OUT_BATCH(_3DSTATE_DRAW_RECT_CMD); 12003b705cfSriastradh OUT_BATCH(DRAW_DITHER_OFS_X(pixmap->drawable.x & 3) | 12103b705cfSriastradh DRAW_DITHER_OFS_Y(pixmap->drawable.y & 3)); 12203b705cfSriastradh OUT_BATCH(0x00000000); /* ymin, xmin */ 12303b705cfSriastradh /* ymax, xmax */ 12403b705cfSriastradh OUT_BATCH((target->drawable.width - 1) | 12503b705cfSriastradh (target->drawable.height - 1) << 16); 12603b705cfSriastradh OUT_BATCH(0x00000000); /* yorigin, xorigin */ 12703b705cfSriastradh 12803b705cfSriastradh OUT_BATCH(_3DSTATE_LOAD_STATE_IMMEDIATE_1 | I1_LOAD_S(2) | 12903b705cfSriastradh I1_LOAD_S(5) | I1_LOAD_S(6) | 2); 13003b705cfSriastradh OUT_BATCH(S2_TEXCOORD_FMT(0, TEXCOORDFMT_2D) | 13103b705cfSriastradh S2_TEXCOORD_FMT(1, TEXCOORDFMT_NOT_PRESENT) | 13203b705cfSriastradh S2_TEXCOORD_FMT(2, TEXCOORDFMT_NOT_PRESENT) | 13303b705cfSriastradh S2_TEXCOORD_FMT(3, TEXCOORDFMT_NOT_PRESENT) | 13403b705cfSriastradh S2_TEXCOORD_FMT(4, TEXCOORDFMT_NOT_PRESENT) | 13503b705cfSriastradh S2_TEXCOORD_FMT(5, TEXCOORDFMT_NOT_PRESENT) | 13603b705cfSriastradh S2_TEXCOORD_FMT(6, TEXCOORDFMT_NOT_PRESENT) | 13703b705cfSriastradh S2_TEXCOORD_FMT(7, TEXCOORDFMT_NOT_PRESENT)); 13803b705cfSriastradh s5 = 0x0; 13903b705cfSriastradh if (intel->cpp == 2) 14003b705cfSriastradh s5 |= S5_COLOR_DITHER_ENABLE; 14103b705cfSriastradh OUT_BATCH(s5); /* S5 - enable bits */ 14203b705cfSriastradh OUT_BATCH((2 << S6_DEPTH_TEST_FUNC_SHIFT) | 14303b705cfSriastradh (2 << S6_CBUF_SRC_BLEND_FACT_SHIFT) | 14403b705cfSriastradh (1 << S6_CBUF_DST_BLEND_FACT_SHIFT) | 14503b705cfSriastradh S6_COLOR_WRITE_ENABLE | (2 << S6_TRISTRIP_PV_SHIFT)); 14603b705cfSriastradh 14703b705cfSriastradh OUT_BATCH(_3DSTATE_CONST_BLEND_COLOR_CMD); 14803b705cfSriastradh OUT_BATCH(0x00000000); 14903b705cfSriastradh 15003b705cfSriastradh OUT_BATCH(_3DSTATE_DST_BUF_VARS_CMD); 15103b705cfSriastradh if (intel->cpp == 2) 15203b705cfSriastradh format = COLR_BUF_RGB565; 15303b705cfSriastradh else 15403b705cfSriastradh format = 15503b705cfSriastradh COLR_BUF_ARGB8888 | DEPTH_FRMT_24_FIXED_8_OTHER; 15603b705cfSriastradh 15703b705cfSriastradh OUT_BATCH(LOD_PRECLAMP_OGL | 15803b705cfSriastradh DSTORG_HORT_BIAS(0x8) | 15903b705cfSriastradh DSTORG_VERT_BIAS(0x8) | format); 16003b705cfSriastradh 16103b705cfSriastradh /* front buffer, pitch, offset */ 16213496ba1Ssnj if (intel_uxa_pixmap_tiled(target)) { 16303b705cfSriastradh tiling = BUF_3D_TILED_SURFACE; 16413496ba1Ssnj if (intel_uxa_get_pixmap_private(target)->tiling == I915_TILING_Y) 16503b705cfSriastradh tiling |= BUF_3D_TILE_WALK_Y; 16603b705cfSriastradh } else 16703b705cfSriastradh tiling = 0; 16803b705cfSriastradh OUT_BATCH(_3DSTATE_BUF_INFO_CMD); 16903b705cfSriastradh OUT_BATCH(BUF_3D_ID_COLOR_BACK | tiling | 17003b705cfSriastradh BUF_3D_PITCH(intel_pixmap_pitch(target))); 17103b705cfSriastradh OUT_RELOC_PIXMAP(target, I915_GEM_DOMAIN_RENDER, 17203b705cfSriastradh I915_GEM_DOMAIN_RENDER, 0); 17303b705cfSriastradh 17403b705cfSriastradh if (!is_planar_fourcc(id)) { 17503b705cfSriastradh FS_LOCALS(); 17603b705cfSriastradh 17703b705cfSriastradh OUT_BATCH(_3DSTATE_PIXEL_SHADER_CONSTANTS | 4); 17803b705cfSriastradh OUT_BATCH(0x0000001); /* constant 0 */ 17903b705cfSriastradh /* constant 0: brightness/contrast */ 18003b705cfSriastradh OUT_BATCH_F(adaptor_priv->brightness / 128.0); 18103b705cfSriastradh OUT_BATCH_F(adaptor_priv->contrast / 255.0); 18203b705cfSriastradh OUT_BATCH_F(0.0); 18303b705cfSriastradh OUT_BATCH_F(0.0); 18403b705cfSriastradh 18503b705cfSriastradh OUT_BATCH(_3DSTATE_SAMPLER_STATE | 3); 18603b705cfSriastradh OUT_BATCH(0x00000001); 18703b705cfSriastradh OUT_BATCH(SS2_COLORSPACE_CONVERSION | 18803b705cfSriastradh (FILTER_LINEAR << SS2_MAG_FILTER_SHIFT) | 18903b705cfSriastradh (FILTER_LINEAR << SS2_MIN_FILTER_SHIFT)); 19003b705cfSriastradh OUT_BATCH((TEXCOORDMODE_CLAMP_EDGE << 19103b705cfSriastradh SS3_TCX_ADDR_MODE_SHIFT) | 19203b705cfSriastradh (TEXCOORDMODE_CLAMP_EDGE << 19303b705cfSriastradh SS3_TCY_ADDR_MODE_SHIFT) | 19403b705cfSriastradh (0 << SS3_TEXTUREMAP_INDEX_SHIFT) | 19503b705cfSriastradh SS3_NORMALIZED_COORDS); 19603b705cfSriastradh OUT_BATCH(0x00000000); 19703b705cfSriastradh 19803b705cfSriastradh OUT_BATCH(_3DSTATE_MAP_STATE | 3); 19903b705cfSriastradh OUT_BATCH(0x00000001); /* texture map #1 */ 20003b705cfSriastradh if (adaptor_priv->buf) 20103b705cfSriastradh OUT_RELOC(adaptor_priv->buf, 20203b705cfSriastradh I915_GEM_DOMAIN_SAMPLER, 0, 20303b705cfSriastradh adaptor_priv->YBufOffset); 20403b705cfSriastradh else 20503b705cfSriastradh OUT_BATCH(adaptor_priv->YBufOffset); 20603b705cfSriastradh 20703b705cfSriastradh ms3 = MAPSURF_422; 20803b705cfSriastradh switch (id) { 20903b705cfSriastradh case FOURCC_YUY2: 21003b705cfSriastradh ms3 |= MT_422_YCRCB_NORMAL; 21103b705cfSriastradh break; 21203b705cfSriastradh case FOURCC_UYVY: 21303b705cfSriastradh ms3 |= MT_422_YCRCB_SWAPY; 21403b705cfSriastradh break; 21503b705cfSriastradh } 21603b705cfSriastradh ms3 |= (height - 1) << MS3_HEIGHT_SHIFT; 21703b705cfSriastradh ms3 |= (width - 1) << MS3_WIDTH_SHIFT; 21803b705cfSriastradh OUT_BATCH(ms3); 21903b705cfSriastradh OUT_BATCH(((video_pitch / 4) - 1) << MS4_PITCH_SHIFT); 22003b705cfSriastradh 22103b705cfSriastradh FS_BEGIN(); 22203b705cfSriastradh i915_fs_dcl(FS_S0); 22303b705cfSriastradh i915_fs_dcl(FS_T0); 22403b705cfSriastradh i915_fs_texld(FS_OC, FS_S0, FS_T0); 22503b705cfSriastradh if (adaptor_priv->brightness != 0) { 22603b705cfSriastradh i915_fs_add(FS_OC, 22703b705cfSriastradh i915_fs_operand_reg(FS_OC), 22803b705cfSriastradh i915_fs_operand(FS_C0, X, X, X, 22903b705cfSriastradh ZERO)); 23003b705cfSriastradh } 23103b705cfSriastradh FS_END(); 23203b705cfSriastradh } else { 23303b705cfSriastradh FS_LOCALS(); 23403b705cfSriastradh 23503b705cfSriastradh /* For the planar formats, we set up three samplers -- 23603b705cfSriastradh * one for each plane, in a Y8 format. Because I 23703b705cfSriastradh * couldn't get the special PLANAR_TO_PACKED 23803b705cfSriastradh * shader setup to work, I did the manual pixel shader: 23903b705cfSriastradh * 24003b705cfSriastradh * y' = y - .0625 24103b705cfSriastradh * u' = u - .5 24203b705cfSriastradh * v' = v - .5; 24303b705cfSriastradh * 24403b705cfSriastradh * r = 1.1643 * y' + 0.0 * u' + 1.5958 * v' 24503b705cfSriastradh * g = 1.1643 * y' - 0.39173 * u' - 0.81290 * v' 24603b705cfSriastradh * b = 1.1643 * y' + 2.017 * u' + 0.0 * v' 24703b705cfSriastradh * 24803b705cfSriastradh * register assignment: 24903b705cfSriastradh * r0 = (y',u',v',0) 25003b705cfSriastradh * r1 = (y,y,y,y) 25103b705cfSriastradh * r2 = (u,u,u,u) 25203b705cfSriastradh * r3 = (v,v,v,v) 25303b705cfSriastradh * OC = (r,g,b,1) 25403b705cfSriastradh */ 25503b705cfSriastradh OUT_BATCH(_3DSTATE_PIXEL_SHADER_CONSTANTS | (22 - 2)); 25603b705cfSriastradh OUT_BATCH(0x000001f); /* constants 0-4 */ 25703b705cfSriastradh /* constant 0: normalization offsets */ 25803b705cfSriastradh OUT_BATCH_F(-0.0625); 25903b705cfSriastradh OUT_BATCH_F(-0.5); 26003b705cfSriastradh OUT_BATCH_F(-0.5); 26103b705cfSriastradh OUT_BATCH_F(0.0); 26203b705cfSriastradh /* constant 1: r coefficients */ 26303b705cfSriastradh OUT_BATCH_F(1.1643); 26403b705cfSriastradh OUT_BATCH_F(0.0); 26503b705cfSriastradh OUT_BATCH_F(1.5958); 26603b705cfSriastradh OUT_BATCH_F(0.0); 26703b705cfSriastradh /* constant 2: g coefficients */ 26803b705cfSriastradh OUT_BATCH_F(1.1643); 26903b705cfSriastradh OUT_BATCH_F(-0.39173); 27003b705cfSriastradh OUT_BATCH_F(-0.81290); 27103b705cfSriastradh OUT_BATCH_F(0.0); 27203b705cfSriastradh /* constant 3: b coefficients */ 27303b705cfSriastradh OUT_BATCH_F(1.1643); 27403b705cfSriastradh OUT_BATCH_F(2.017); 27503b705cfSriastradh OUT_BATCH_F(0.0); 27603b705cfSriastradh OUT_BATCH_F(0.0); 27703b705cfSriastradh /* constant 4: brightness/contrast */ 27803b705cfSriastradh OUT_BATCH_F(adaptor_priv->brightness / 128.0); 27903b705cfSriastradh OUT_BATCH_F(adaptor_priv->contrast / 255.0); 28003b705cfSriastradh OUT_BATCH_F(0.0); 28103b705cfSriastradh OUT_BATCH_F(0.0); 28203b705cfSriastradh 28303b705cfSriastradh OUT_BATCH(_3DSTATE_SAMPLER_STATE | 9); 28403b705cfSriastradh OUT_BATCH(0x00000007); 28503b705cfSriastradh /* sampler 0 */ 28603b705cfSriastradh OUT_BATCH((FILTER_LINEAR << SS2_MAG_FILTER_SHIFT) | 28703b705cfSriastradh (FILTER_LINEAR << SS2_MIN_FILTER_SHIFT)); 28803b705cfSriastradh OUT_BATCH((TEXCOORDMODE_CLAMP_EDGE << 28903b705cfSriastradh SS3_TCX_ADDR_MODE_SHIFT) | 29003b705cfSriastradh (TEXCOORDMODE_CLAMP_EDGE << 29103b705cfSriastradh SS3_TCY_ADDR_MODE_SHIFT) | 29203b705cfSriastradh (0 << SS3_TEXTUREMAP_INDEX_SHIFT) | 29303b705cfSriastradh SS3_NORMALIZED_COORDS); 29403b705cfSriastradh OUT_BATCH(0x00000000); 29503b705cfSriastradh /* sampler 1 */ 29603b705cfSriastradh OUT_BATCH((FILTER_LINEAR << SS2_MAG_FILTER_SHIFT) | 29703b705cfSriastradh (FILTER_LINEAR << SS2_MIN_FILTER_SHIFT)); 29803b705cfSriastradh OUT_BATCH((TEXCOORDMODE_CLAMP_EDGE << 29903b705cfSriastradh SS3_TCX_ADDR_MODE_SHIFT) | 30003b705cfSriastradh (TEXCOORDMODE_CLAMP_EDGE << 30103b705cfSriastradh SS3_TCY_ADDR_MODE_SHIFT) | 30203b705cfSriastradh (1 << SS3_TEXTUREMAP_INDEX_SHIFT) | 30303b705cfSriastradh SS3_NORMALIZED_COORDS); 30403b705cfSriastradh OUT_BATCH(0x00000000); 30503b705cfSriastradh /* sampler 2 */ 30603b705cfSriastradh OUT_BATCH((FILTER_LINEAR << SS2_MAG_FILTER_SHIFT) | 30703b705cfSriastradh (FILTER_LINEAR << SS2_MIN_FILTER_SHIFT)); 30803b705cfSriastradh OUT_BATCH((TEXCOORDMODE_CLAMP_EDGE << 30903b705cfSriastradh SS3_TCX_ADDR_MODE_SHIFT) | 31003b705cfSriastradh (TEXCOORDMODE_CLAMP_EDGE << 31103b705cfSriastradh SS3_TCY_ADDR_MODE_SHIFT) | 31203b705cfSriastradh (2 << SS3_TEXTUREMAP_INDEX_SHIFT) | 31303b705cfSriastradh SS3_NORMALIZED_COORDS); 31403b705cfSriastradh OUT_BATCH(0x00000000); 31503b705cfSriastradh 31603b705cfSriastradh OUT_BATCH(_3DSTATE_MAP_STATE | 9); 31703b705cfSriastradh OUT_BATCH(0x00000007); 31803b705cfSriastradh 31903b705cfSriastradh if (adaptor_priv->buf) 32003b705cfSriastradh OUT_RELOC(adaptor_priv->buf, 32103b705cfSriastradh I915_GEM_DOMAIN_SAMPLER, 0, 32203b705cfSriastradh adaptor_priv->YBufOffset); 32303b705cfSriastradh else 32403b705cfSriastradh OUT_BATCH(adaptor_priv->YBufOffset); 32503b705cfSriastradh 32603b705cfSriastradh ms3 = MAPSURF_8BIT | MT_8BIT_I8; 32703b705cfSriastradh ms3 |= (height - 1) << MS3_HEIGHT_SHIFT; 32803b705cfSriastradh ms3 |= (width - 1) << MS3_WIDTH_SHIFT; 32903b705cfSriastradh OUT_BATCH(ms3); 33003b705cfSriastradh /* check to see if Y has special pitch than normal 33103b705cfSriastradh * double u/v pitch, e.g i915 XvMC hw requires at 33203b705cfSriastradh * least 1K alignment, so Y pitch might 33303b705cfSriastradh * be same as U/V's.*/ 33403b705cfSriastradh if (video_pitch2) 33503b705cfSriastradh OUT_BATCH(((video_pitch2 / 4) - 33603b705cfSriastradh 1) << MS4_PITCH_SHIFT); 33703b705cfSriastradh else 33803b705cfSriastradh OUT_BATCH(((video_pitch * 2 / 4) - 33903b705cfSriastradh 1) << MS4_PITCH_SHIFT); 34003b705cfSriastradh 34103b705cfSriastradh if (adaptor_priv->buf) 34203b705cfSriastradh OUT_RELOC(adaptor_priv->buf, 34303b705cfSriastradh I915_GEM_DOMAIN_SAMPLER, 0, 34403b705cfSriastradh adaptor_priv->UBufOffset); 34503b705cfSriastradh else 34603b705cfSriastradh OUT_BATCH(adaptor_priv->UBufOffset); 34703b705cfSriastradh 34803b705cfSriastradh ms3 = MAPSURF_8BIT | MT_8BIT_I8; 34903b705cfSriastradh ms3 |= (height / 2 - 1) << MS3_HEIGHT_SHIFT; 35003b705cfSriastradh ms3 |= (width / 2 - 1) << MS3_WIDTH_SHIFT; 35103b705cfSriastradh OUT_BATCH(ms3); 35203b705cfSriastradh OUT_BATCH(((video_pitch / 4) - 1) << MS4_PITCH_SHIFT); 35303b705cfSriastradh 35403b705cfSriastradh if (adaptor_priv->buf) 35503b705cfSriastradh OUT_RELOC(adaptor_priv->buf, 35603b705cfSriastradh I915_GEM_DOMAIN_SAMPLER, 0, 35703b705cfSriastradh adaptor_priv->VBufOffset); 35803b705cfSriastradh else 35903b705cfSriastradh OUT_BATCH(adaptor_priv->VBufOffset); 36003b705cfSriastradh 36103b705cfSriastradh ms3 = MAPSURF_8BIT | MT_8BIT_I8; 36203b705cfSriastradh ms3 |= (height / 2 - 1) << MS3_HEIGHT_SHIFT; 36303b705cfSriastradh ms3 |= (width / 2 - 1) << MS3_WIDTH_SHIFT; 36403b705cfSriastradh OUT_BATCH(ms3); 36503b705cfSriastradh OUT_BATCH(((video_pitch / 4) - 1) << MS4_PITCH_SHIFT); 36603b705cfSriastradh 36703b705cfSriastradh FS_BEGIN(); 36803b705cfSriastradh /* Declare samplers */ 36903b705cfSriastradh i915_fs_dcl(FS_S0); /* Y */ 37003b705cfSriastradh i915_fs_dcl(FS_S1); /* U */ 37103b705cfSriastradh i915_fs_dcl(FS_S2); /* V */ 37203b705cfSriastradh i915_fs_dcl(FS_T0); /* normalized coords */ 37303b705cfSriastradh 37403b705cfSriastradh /* Load samplers to temporaries. */ 37503b705cfSriastradh i915_fs_texld(FS_R1, FS_S0, FS_T0); 37603b705cfSriastradh i915_fs_texld(FS_R2, FS_S1, FS_T0); 37703b705cfSriastradh i915_fs_texld(FS_R3, FS_S2, FS_T0); 37803b705cfSriastradh 37903b705cfSriastradh /* Move the sampled YUV data in R[123] to the first 38003b705cfSriastradh * 3 channels of R0. 38103b705cfSriastradh */ 38203b705cfSriastradh i915_fs_mov_masked(FS_R0, MASK_X, 38303b705cfSriastradh i915_fs_operand_reg(FS_R1)); 38403b705cfSriastradh i915_fs_mov_masked(FS_R0, MASK_Y, 38503b705cfSriastradh i915_fs_operand_reg(FS_R2)); 38603b705cfSriastradh i915_fs_mov_masked(FS_R0, MASK_Z, 38703b705cfSriastradh i915_fs_operand_reg(FS_R3)); 38803b705cfSriastradh 38903b705cfSriastradh /* Normalize the YUV data */ 39003b705cfSriastradh i915_fs_add(FS_R0, i915_fs_operand_reg(FS_R0), 39103b705cfSriastradh i915_fs_operand_reg(FS_C0)); 39203b705cfSriastradh /* dot-product the YUV data in R0 by the vectors of 39303b705cfSriastradh * coefficients for calculating R, G, and B, storing 39403b705cfSriastradh * the results in the R, G, or B channels of the output 39503b705cfSriastradh * color. The OC results are implicitly clamped 39603b705cfSriastradh * at the end of the program. 39703b705cfSriastradh */ 39803b705cfSriastradh i915_fs_dp3(FS_OC, MASK_X, 39903b705cfSriastradh i915_fs_operand_reg(FS_R0), 40003b705cfSriastradh i915_fs_operand_reg(FS_C1)); 40103b705cfSriastradh i915_fs_dp3(FS_OC, MASK_Y, 40203b705cfSriastradh i915_fs_operand_reg(FS_R0), 40303b705cfSriastradh i915_fs_operand_reg(FS_C2)); 40403b705cfSriastradh i915_fs_dp3(FS_OC, MASK_Z, 40503b705cfSriastradh i915_fs_operand_reg(FS_R0), 40603b705cfSriastradh i915_fs_operand_reg(FS_C3)); 40703b705cfSriastradh /* Set alpha of the output to 1.0, by wiring W to 1 40803b705cfSriastradh * and not actually using the source. 40903b705cfSriastradh */ 41003b705cfSriastradh i915_fs_mov_masked(FS_OC, MASK_W, 41103b705cfSriastradh i915_fs_operand_one()); 41203b705cfSriastradh 41303b705cfSriastradh if (adaptor_priv->brightness != 0) { 41403b705cfSriastradh i915_fs_add(FS_OC, 41503b705cfSriastradh i915_fs_operand_reg(FS_OC), 41603b705cfSriastradh i915_fs_operand(FS_C4, X, X, X, 41703b705cfSriastradh ZERO)); 41803b705cfSriastradh } 41903b705cfSriastradh FS_END(); 42003b705cfSriastradh } 42103b705cfSriastradh 42203b705cfSriastradh OUT_BATCH(PRIM3D_RECTLIST | (12 * nbox_this_time - 1)); 42303b705cfSriastradh while (nbox_this_time--) { 42403b705cfSriastradh int box_x1 = pbox->x1; 42503b705cfSriastradh int box_y1 = pbox->y1; 42603b705cfSriastradh int box_x2 = pbox->x2; 42703b705cfSriastradh int box_y2 = pbox->y2; 42803b705cfSriastradh float src_scale_x, src_scale_y; 42903b705cfSriastradh 43003b705cfSriastradh pbox++; 43103b705cfSriastradh 43203b705cfSriastradh src_scale_x = ((float)src_w / width) / drw_w; 43303b705cfSriastradh src_scale_y = ((float)src_h / height) / drw_h; 43403b705cfSriastradh 43503b705cfSriastradh /* vertex data - rect list consists of bottom right, 43603b705cfSriastradh * bottom left, and top left vertices. 43703b705cfSriastradh */ 43803b705cfSriastradh 43903b705cfSriastradh /* bottom right */ 44003b705cfSriastradh OUT_BATCH_F(box_x2 + pix_xoff); 44103b705cfSriastradh OUT_BATCH_F(box_y2 + pix_yoff); 44203b705cfSriastradh OUT_BATCH_F((box_x2 - dxo) * src_scale_x); 44303b705cfSriastradh OUT_BATCH_F((box_y2 - dyo) * src_scale_y); 44403b705cfSriastradh 44503b705cfSriastradh /* bottom left */ 44603b705cfSriastradh OUT_BATCH_F(box_x1 + pix_xoff); 44703b705cfSriastradh OUT_BATCH_F(box_y2 + pix_yoff); 44803b705cfSriastradh OUT_BATCH_F((box_x1 - dxo) * src_scale_x); 44903b705cfSriastradh OUT_BATCH_F((box_y2 - dyo) * src_scale_y); 45003b705cfSriastradh 45103b705cfSriastradh /* top left */ 45203b705cfSriastradh OUT_BATCH_F(box_x1 + pix_xoff); 45303b705cfSriastradh OUT_BATCH_F(box_y1 + pix_yoff); 45403b705cfSriastradh OUT_BATCH_F((box_x1 - dxo) * src_scale_x); 45503b705cfSriastradh OUT_BATCH_F((box_y1 - dyo) * src_scale_y); 45603b705cfSriastradh } 45703b705cfSriastradh 45803b705cfSriastradh intel_batch_end_atomic(scrn); 45903b705cfSriastradh } 46003b705cfSriastradh 46103b705cfSriastradh if (target != pixmap) { 46203b705cfSriastradh GCPtr gc; 46303b705cfSriastradh 46403b705cfSriastradh gc = GetScratchGC(pixmap->drawable.depth, 46503b705cfSriastradh pixmap->drawable.pScreen); 46603b705cfSriastradh if (gc) { 46703b705cfSriastradh gc->subWindowMode = ClipByChildren; 46803b705cfSriastradh 46903b705cfSriastradh if (REGION_NUM_RECTS(dstRegion) > 1) { 47003b705cfSriastradh RegionPtr tmp; 47103b705cfSriastradh 47203b705cfSriastradh tmp = REGION_CREATE(pixmap->drawable.pScreen, NULL, 0); 47303b705cfSriastradh if (tmp) { 47403b705cfSriastradh REGION_COPY(pixmap->drawable.pScreen, tmp, dstRegion); 47503b705cfSriastradh gc->funcs->ChangeClip(gc, CT_REGION, tmp, 0); 47603b705cfSriastradh } 47703b705cfSriastradh } 47803b705cfSriastradh 47903b705cfSriastradh ValidateGC(&pixmap->drawable, gc); 48003b705cfSriastradh gc->ops->CopyArea(&target->drawable, &pixmap->drawable, gc, 48103b705cfSriastradh 0, 0, 48203b705cfSriastradh target->drawable.width, 48303b705cfSriastradh target->drawable.height, 48403b705cfSriastradh -pix_xoff, -pix_yoff); 48503b705cfSriastradh FreeScratchGC(gc); 48603b705cfSriastradh } 48703b705cfSriastradh 48803b705cfSriastradh target->drawable.pScreen->DestroyPixmap(target); 48903b705cfSriastradh } 49003b705cfSriastradh 49113496ba1Ssnj intel_uxa_debug_flush(scrn); 49203b705cfSriastradh} 493