vl_idct.c revision 74c71f09f3d321963b738acfb0bfd30b1e1efaeb
1508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König/**************************************************************************
2508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König *
3508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König * Copyright 2010 Christian König
4508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König * All Rights Reserved.
5508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König *
6508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König * Permission is hereby granted, free of charge, to any person obtaining a
7508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König * copy of this software and associated documentation files (the
8508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König * "Software"), to deal in the Software without restriction, including
9508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König * without limitation the rights to use, copy, modify, merge, publish,
10508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König * distribute, sub license, and/or sell copies of the Software, and to
11508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König * permit persons to whom the Software is furnished to do so, subject to
12508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König * the following conditions:
13508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König *
14508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König * The above copyright notice and this permission notice (including the
15508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König * next paragraph) shall be included in all copies or substantial portions
16508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König * of the Software.
17508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König *
18508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
19508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
20508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT.
21508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König * IN NO EVENT SHALL TUNGSTEN GRAPHICS AND/OR ITS SUPPLIERS BE LIABLE FOR
22508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König * ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
23508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König * TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
24508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König * SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
25508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König *
26508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König **************************************************************************/
27508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
28508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König#include "vl_idct.h"
294abe7382882a451a7750ccc451b8568768d122cbChristian König#include "vl_vertex_buffers.h"
30e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König#include "util/u_draw.h"
31508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König#include <assert.h>
32508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König#include <pipe/p_context.h>
33508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König#include <pipe/p_screen.h>
34508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König#include <util/u_inlines.h>
35508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König#include <util/u_sampler.h>
36508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König#include <util/u_format.h>
37508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König#include <tgsi/tgsi_ureg.h>
38508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König#include "vl_types.h"
39508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
40508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König#define BLOCK_WIDTH 8
41508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König#define BLOCK_HEIGHT 8
42ac1fd50163119a887487d748fab507b23e215c2bChristian König
4303c5a0ea5cd5b3e5931d6784749f87789a016b98Christian König#define SCALE_FACTOR_16_TO_9 (32768.0f / 256.0f)
44508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
45ed49905944243863913bc2598f734ca038c85b94Christian König#define STAGE1_SCALE 4.0f
46ed49905944243863913bc2598f734ca038c85b94Christian König#define STAGE2_SCALE (SCALE_FACTOR_16_TO_9 / STAGE1_SCALE)
47ed49905944243863913bc2598f734ca038c85b94Christian König
48a984c67b316ac2ca9aaf6d38a3127cf3d61a249eChristian König#define NR_RENDER_TARGETS 1
49a984c67b316ac2ca9aaf6d38a3127cf3d61a249eChristian König
50508a4a056c3140dc1f90b93acd46c06c30f7094eChristian Königstruct vertex_shader_consts
51508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König{
52508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   struct vertex4f norm;
53508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König};
54508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
55508a4a056c3140dc1f90b93acd46c06c30f7094eChristian Königenum VS_INPUT
56508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König{
57508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   VS_I_RECT,
58508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   VS_I_VPOS,
59508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
60508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   NUM_VS_INPUTS
61508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König};
62508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
63508a4a056c3140dc1f90b93acd46c06c30f7094eChristian Königenum VS_OUTPUT
64508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König{
65508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   VS_O_VPOS,
66508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   VS_O_BLOCK,
67508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   VS_O_TEX,
687408a6ab89e0bc87209b50334604fae93277fdc6Christian König   VS_O_START
69508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König};
70508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
71e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian Königstatic const float const_matrix[8][8] = {
72508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   {  0.3535530f,  0.3535530f,  0.3535530f,  0.3535530f,  0.3535530f,  0.3535530f,  0.353553f,  0.3535530f },
73508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   {  0.4903930f,  0.4157350f,  0.2777850f,  0.0975451f, -0.0975452f, -0.2777850f, -0.415735f, -0.4903930f },
74508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   {  0.4619400f,  0.1913420f, -0.1913420f, -0.4619400f, -0.4619400f, -0.1913420f,  0.191342f,  0.4619400f },
75508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   {  0.4157350f, -0.0975452f, -0.4903930f, -0.2777850f,  0.2777850f,  0.4903930f,  0.097545f, -0.4157350f },
76508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   {  0.3535530f, -0.3535530f, -0.3535530f,  0.3535540f,  0.3535530f, -0.3535540f, -0.353553f,  0.3535530f },
77508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   {  0.2777850f, -0.4903930f,  0.0975452f,  0.4157350f, -0.4157350f, -0.0975451f,  0.490393f, -0.2777850f },
78508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   {  0.1913420f, -0.4619400f,  0.4619400f, -0.1913420f, -0.1913410f,  0.4619400f, -0.461940f,  0.1913420f },
79508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   {  0.0975451f, -0.2777850f,  0.4157350f, -0.4903930f,  0.4903930f, -0.4157350f,  0.277786f, -0.0975458f }
80508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König};
81508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
82508a4a056c3140dc1f90b93acd46c06c30f7094eChristian Königstatic void *
83e742a1043dbd56fe11f0490cb74b7a738bab2238Christian Königcreate_vert_shader(struct vl_idct *idct, bool calc_src_cords)
84508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König{
85508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   struct ureg_program *shader;
867408a6ab89e0bc87209b50334604fae93277fdc6Christian König   struct ureg_src scale;
87508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   struct ureg_src vrect, vpos;
887408a6ab89e0bc87209b50334604fae93277fdc6Christian König   struct ureg_dst t_vpos;
897408a6ab89e0bc87209b50334604fae93277fdc6Christian König   struct ureg_dst o_vpos, o_block, o_tex, o_start;
90508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
91508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   shader = ureg_create(TGSI_PROCESSOR_VERTEX);
92508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   if (!shader)
93508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König      return NULL;
94508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
95508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   t_vpos = ureg_DECL_temporary(shader);
96508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
97508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   vrect = ureg_DECL_vs_input(shader, VS_I_RECT);
98508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   vpos = ureg_DECL_vs_input(shader, VS_I_VPOS);
99508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
100508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   o_vpos = ureg_DECL_output(shader, TGSI_SEMANTIC_POSITION, VS_O_VPOS);
101508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
102508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   /*
10312836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König    * scale = (BLOCK_WIDTH, BLOCK_HEIGHT) / (dst.width, dst.height)
10412836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König    *
105508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König    * t_vpos = vpos + vrect
106508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König    * o_vpos.xy = t_vpos * scale
107508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König    * o_vpos.zw = vpos
108508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König    *
109508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König    * o_block = vrect
110508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König    * o_tex = t_pos
111508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König    * o_start = vpos * scale
112508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König    *
113508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König    */
11412836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König   scale = ureg_imm2f(shader,
115e742a1043dbd56fe11f0490cb74b7a738bab2238Christian König      (float)BLOCK_WIDTH / idct->destination->width0,
116e742a1043dbd56fe11f0490cb74b7a738bab2238Christian König      (float)BLOCK_HEIGHT / idct->destination->height0);
11712836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König
118508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   ureg_ADD(shader, ureg_writemask(t_vpos, TGSI_WRITEMASK_XY), vpos, vrect);
1197408a6ab89e0bc87209b50334604fae93277fdc6Christian König   ureg_MUL(shader, ureg_writemask(t_vpos, TGSI_WRITEMASK_XY), ureg_src(t_vpos), scale);
120508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   ureg_MOV(shader, ureg_writemask(o_vpos, TGSI_WRITEMASK_XY), ureg_src(t_vpos));
121508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   ureg_MOV(shader, ureg_writemask(o_vpos, TGSI_WRITEMASK_ZW), vpos);
122508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
12312836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König   if(calc_src_cords) {
12412836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König      o_block = ureg_DECL_output(shader, TGSI_SEMANTIC_GENERIC, VS_O_BLOCK);
12512836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König      o_tex = ureg_DECL_output(shader, TGSI_SEMANTIC_GENERIC, VS_O_TEX);
12612836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König      o_start = ureg_DECL_output(shader, TGSI_SEMANTIC_GENERIC, VS_O_START);
12712836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König
12812836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König      ureg_MOV(shader, ureg_writemask(o_block, TGSI_WRITEMASK_XY), vrect);
12912836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König      ureg_MOV(shader, ureg_writemask(o_tex, TGSI_WRITEMASK_XY), ureg_src(t_vpos));
13012836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König      ureg_MUL(shader, ureg_writemask(o_start, TGSI_WRITEMASK_XY), vpos, scale);
13112836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König   }
132508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
133508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   ureg_release_temporary(shader, t_vpos);
134508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
135508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   ureg_END(shader);
136508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
137508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   return ureg_create_shader_and_destroy(shader, idct->pipe);
138508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König}
139508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
140508a4a056c3140dc1f90b93acd46c06c30f7094eChristian Königstatic void
141cfe489b89723117e56674c2be7761c201f8d78ffChristian Königfetch_four(struct ureg_program *shader, struct ureg_dst m[2],
142cfe489b89723117e56674c2be7761c201f8d78ffChristian König           struct ureg_src tc, struct ureg_src sampler,
14374c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König           struct ureg_src start, struct ureg_src block,
14474c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König           bool right_side, bool transposed, float size)
145cfe489b89723117e56674c2be7761c201f8d78ffChristian König{
146cfe489b89723117e56674c2be7761c201f8d78ffChristian König   struct ureg_dst t_tc;
14774c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König   unsigned wm_start = (right_side == transposed) ? TGSI_WRITEMASK_X : TGSI_WRITEMASK_Y;
14874c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König   unsigned wm_tc = (right_side == transposed) ? TGSI_WRITEMASK_Y : TGSI_WRITEMASK_X;
149cfe489b89723117e56674c2be7761c201f8d78ffChristian König
150cfe489b89723117e56674c2be7761c201f8d78ffChristian König   t_tc = ureg_DECL_temporary(shader);
151cfe489b89723117e56674c2be7761c201f8d78ffChristian König   m[0] = ureg_DECL_temporary(shader);
152cfe489b89723117e56674c2be7761c201f8d78ffChristian König   m[1] = ureg_DECL_temporary(shader);
153cfe489b89723117e56674c2be7761c201f8d78ffChristian König
154508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   /*
155cfe489b89723117e56674c2be7761c201f8d78ffChristian König    * t_tc.x = right_side ? start.x : tc.x
156cfe489b89723117e56674c2be7761c201f8d78ffChristian König    * t_tc.y = right_side ? tc.y : start.y
157cfe489b89723117e56674c2be7761c201f8d78ffChristian König    * m[0..1] = tex(t_tc++, sampler)
158508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König    */
15974c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König   if(!right_side) {
16074c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König      ureg_MOV(shader, ureg_writemask(t_tc, wm_start), ureg_scalar(start, TGSI_SWIZZLE_X));
16174c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König      ureg_MOV(shader, ureg_writemask(t_tc, wm_tc), ureg_scalar(tc, TGSI_SWIZZLE_Y));
162ed8b767a8e09cff4d98a44cdc07b08f1b322c4d3Christian König   } else {
16374c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König      ureg_MOV(shader, ureg_writemask(t_tc, wm_start), ureg_scalar(start, TGSI_SWIZZLE_Y));
16474c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König      ureg_MOV(shader, ureg_writemask(t_tc, wm_tc), ureg_scalar(tc, TGSI_SWIZZLE_X));
165ed8b767a8e09cff4d98a44cdc07b08f1b322c4d3Christian König   }
166508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
16774c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König#if NR_RENDER_TARGETS == 8
16874c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König   ureg_MOV(shader, ureg_writemask(t_tc, TGSI_WRITEMASK_Z), ureg_scalar(block, TGSI_SWIZZLE_X));
16974c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König#else
17074c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König   ureg_MOV(shader, ureg_writemask(t_tc, TGSI_WRITEMASK_Z), ureg_imm1f(shader, 0.0f));
17174c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König#endif
17274c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König
17374c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König   ureg_TEX(shader, m[0], TGSI_TEXTURE_3D, ureg_src(t_tc), sampler);
17474c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König   ureg_ADD(shader, ureg_writemask(t_tc, wm_start), ureg_src(t_tc), ureg_imm1f(shader, 1.0f / size));
17574c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König   ureg_TEX(shader, m[1], TGSI_TEXTURE_3D, ureg_src(t_tc), sampler);
176508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
177cfe489b89723117e56674c2be7761c201f8d78ffChristian König   ureg_release_temporary(shader, t_tc);
178cfe489b89723117e56674c2be7761c201f8d78ffChristian König}
179508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
18012836fbcfad7f317b1f5aa5e46f9946894bf040cChristian Königstatic void
18112836fbcfad7f317b1f5aa5e46f9946894bf040cChristian Königmatrix_mul(struct ureg_program *shader, struct ureg_dst dst, struct ureg_dst l[2], struct ureg_dst r[2])
182cfe489b89723117e56674c2be7761c201f8d78ffChristian König{
18312836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König   struct ureg_dst tmp[2];
184cfe489b89723117e56674c2be7761c201f8d78ffChristian König   unsigned i;
185cfe489b89723117e56674c2be7761c201f8d78ffChristian König
186cfe489b89723117e56674c2be7761c201f8d78ffChristian König   for(i = 0; i < 2; ++i) {
187cfe489b89723117e56674c2be7761c201f8d78ffChristian König      tmp[i] = ureg_DECL_temporary(shader);
188508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   }
189508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
190cfe489b89723117e56674c2be7761c201f8d78ffChristian König   /*
191cfe489b89723117e56674c2be7761c201f8d78ffChristian König    * tmp[0..1] = dot4(m[0][0..1], m[1][0..1])
192cfe489b89723117e56674c2be7761c201f8d78ffChristian König    * dst = tmp[0] + tmp[1]
193cfe489b89723117e56674c2be7761c201f8d78ffChristian König    */
19412836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König   ureg_DP4(shader, ureg_writemask(tmp[0], TGSI_WRITEMASK_X), ureg_src(l[0]), ureg_src(r[0]));
19512836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König   ureg_DP4(shader, ureg_writemask(tmp[1], TGSI_WRITEMASK_X), ureg_src(l[1]), ureg_src(r[1]));
19674c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König   ureg_ADD(shader, dst,
19774c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König      ureg_scalar(ureg_src(tmp[0]), TGSI_SWIZZLE_X),
19874c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König      ureg_scalar(ureg_src(tmp[1]), TGSI_SWIZZLE_X));
199508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
200508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   for(i = 0; i < 2; ++i) {
201508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König      ureg_release_temporary(shader, tmp[i]);
202508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   }
203508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König}
204508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
205508a4a056c3140dc1f90b93acd46c06c30f7094eChristian Königstatic void *
206508a4a056c3140dc1f90b93acd46c06c30f7094eChristian Königcreate_transpose_frag_shader(struct vl_idct *idct)
207508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König{
20812836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König   struct pipe_resource *transpose = idct->textures.individual.transpose;
20912836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König   struct pipe_resource *intermediate = idct->textures.individual.intermediate;
21012836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König
211508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   struct ureg_program *shader;
212cfe489b89723117e56674c2be7761c201f8d78ffChristian König
213e742a1043dbd56fe11f0490cb74b7a738bab2238Christian König   struct ureg_src block, tex, sampler[2];
214cfe489b89723117e56674c2be7761c201f8d78ffChristian König   struct ureg_src start[2];
215cfe489b89723117e56674c2be7761c201f8d78ffChristian König
216cfe489b89723117e56674c2be7761c201f8d78ffChristian König   struct ureg_dst m[2][2];
217cfe489b89723117e56674c2be7761c201f8d78ffChristian König   struct ureg_dst tmp, fragment;
218508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
219508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   shader = ureg_create(TGSI_PROCESSOR_FRAGMENT);
220508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   if (!shader)
221508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König      return NULL;
222508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
223e742a1043dbd56fe11f0490cb74b7a738bab2238Christian König   block = ureg_DECL_fs_input(shader, TGSI_SEMANTIC_GENERIC, VS_O_BLOCK, TGSI_INTERPOLATE_LINEAR);
224e742a1043dbd56fe11f0490cb74b7a738bab2238Christian König   tex = ureg_DECL_fs_input(shader, TGSI_SEMANTIC_GENERIC, VS_O_TEX, TGSI_INTERPOLATE_CONSTANT);
225508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
226508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   sampler[0] = ureg_DECL_sampler(shader, 0);
2272c9db2484b7c1cec7a3a629f70a5aa840e16268eChristian König   sampler[1] = ureg_DECL_sampler(shader, 1);
228508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
229cfe489b89723117e56674c2be7761c201f8d78ffChristian König   start[0] = ureg_imm1f(shader, 0.0f);
230cfe489b89723117e56674c2be7761c201f8d78ffChristian König   start[1] = ureg_DECL_fs_input(shader, TGSI_SEMANTIC_GENERIC, VS_O_START, TGSI_INTERPOLATE_CONSTANT);
231cfe489b89723117e56674c2be7761c201f8d78ffChristian König
23274c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König   fetch_four(shader, m[0], block, sampler[0], start[0], block, false, false, transpose->width0);
23374c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König   fetch_four(shader, m[1], tex, sampler[1], start[1], block, true, false, intermediate->height0);
234c9e10c666adc64f6c5dfb04422560508f115aa54Christian König
235508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   fragment = ureg_DECL_output(shader, TGSI_SEMANTIC_COLOR, 0);
236508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
23712836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König   tmp = ureg_DECL_temporary(shader);
23812836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König   matrix_mul(shader, ureg_writemask(tmp, TGSI_WRITEMASK_X), m[0], m[1]);
23913e28cff7655adec0f89aed9c5ee74f8481133abChristian König   ureg_MUL(shader, fragment, ureg_src(tmp), ureg_imm1f(shader, STAGE2_SCALE));
240cfe489b89723117e56674c2be7761c201f8d78ffChristian König
241cfe489b89723117e56674c2be7761c201f8d78ffChristian König   ureg_release_temporary(shader, tmp);
242cfe489b89723117e56674c2be7761c201f8d78ffChristian König   ureg_release_temporary(shader, m[0][0]);
243cfe489b89723117e56674c2be7761c201f8d78ffChristian König   ureg_release_temporary(shader, m[0][1]);
244cfe489b89723117e56674c2be7761c201f8d78ffChristian König   ureg_release_temporary(shader, m[1][0]);
245cfe489b89723117e56674c2be7761c201f8d78ffChristian König   ureg_release_temporary(shader, m[1][1]);
24603c5a0ea5cd5b3e5931d6784749f87789a016b98Christian König
247508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   ureg_END(shader);
248508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
249508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   return ureg_create_shader_and_destroy(shader, idct->pipe);
250508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König}
251508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
252508a4a056c3140dc1f90b93acd46c06c30f7094eChristian Königstatic void *
253508a4a056c3140dc1f90b93acd46c06c30f7094eChristian Königcreate_matrix_frag_shader(struct vl_idct *idct)
254508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König{
25512836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König   struct pipe_resource *matrix = idct->textures.individual.matrix;
25612836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König   struct pipe_resource *source = idct->textures.individual.source;
25712836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König
258508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   struct ureg_program *shader;
259cfe489b89723117e56674c2be7761c201f8d78ffChristian König
26074c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König   struct ureg_src tex, block, sampler[2];
261cfe489b89723117e56674c2be7761c201f8d78ffChristian König   struct ureg_src start[2];
262cfe489b89723117e56674c2be7761c201f8d78ffChristian König
26374c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König   struct ureg_dst l[4][2], r[2];
264a984c67b316ac2ca9aaf6d38a3127cf3d61a249eChristian König   struct ureg_dst t_tc, tmp, fragment[NR_RENDER_TARGETS];
26512836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König
26674c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König   unsigned i, j;
267508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
268508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   shader = ureg_create(TGSI_PROCESSOR_FRAGMENT);
269508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   if (!shader)
270508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König      return NULL;
271508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
27212836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König   t_tc = ureg_DECL_temporary(shader);
27312836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König   tmp = ureg_DECL_temporary(shader);
27412836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König
27574c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König   tex = ureg_DECL_fs_input(shader, TGSI_SEMANTIC_GENERIC, VS_O_TEX, TGSI_INTERPOLATE_LINEAR);
27674c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König   block = ureg_DECL_fs_input(shader, TGSI_SEMANTIC_GENERIC, VS_O_BLOCK, TGSI_INTERPOLATE_LINEAR);
277508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
2782c9db2484b7c1cec7a3a629f70a5aa840e16268eChristian König   sampler[0] = ureg_DECL_sampler(shader, 1);
2792c9db2484b7c1cec7a3a629f70a5aa840e16268eChristian König   sampler[1] = ureg_DECL_sampler(shader, 0);
280508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
281cfe489b89723117e56674c2be7761c201f8d78ffChristian König   start[0] = ureg_DECL_fs_input(shader, TGSI_SEMANTIC_GENERIC, VS_O_START, TGSI_INTERPOLATE_CONSTANT);
282cfe489b89723117e56674c2be7761c201f8d78ffChristian König   start[1] = ureg_imm1f(shader, 0.0f);
283cfe489b89723117e56674c2be7761c201f8d78ffChristian König
284a984c67b316ac2ca9aaf6d38a3127cf3d61a249eChristian König   for (i = 0; i < NR_RENDER_TARGETS; ++i)
285e742a1043dbd56fe11f0490cb74b7a738bab2238Christian König       fragment[i] = ureg_DECL_output(shader, TGSI_SEMANTIC_COLOR, i);
286e742a1043dbd56fe11f0490cb74b7a738bab2238Christian König
28774c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König   /* pixel center is at 0.5 not 0.0 !!! */
28874c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König   ureg_ADD(shader, ureg_writemask(t_tc, TGSI_WRITEMASK_Y),
28974c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König      tex, ureg_imm1f(shader, -2.0f / source->height0));
29074c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König
29174c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König   for (i = 0; i < 4; ++i) {
29274c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König      fetch_four(shader, l[i], ureg_src(t_tc), sampler[0], start[0], block, false, false, source->width0);
29374c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König      ureg_MUL(shader, l[i][0], ureg_src(l[i][0]), ureg_imm1f(shader, STAGE1_SCALE));
29474c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König      ureg_MUL(shader, l[i][1], ureg_src(l[i][1]), ureg_imm1f(shader, STAGE1_SCALE));
29574c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König      if(i != 3)
29674c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König         ureg_ADD(shader, ureg_writemask(t_tc, TGSI_WRITEMASK_Y),
29774c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König            ureg_src(t_tc), ureg_imm1f(shader, 1.0f / source->height0));
29874c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König   }
299e742a1043dbd56fe11f0490cb74b7a738bab2238Christian König
300a984c67b316ac2ca9aaf6d38a3127cf3d61a249eChristian König   for (i = 0; i < NR_RENDER_TARGETS; ++i) {
301a984c67b316ac2ca9aaf6d38a3127cf3d61a249eChristian König
302a984c67b316ac2ca9aaf6d38a3127cf3d61a249eChristian König#if NR_RENDER_TARGETS == 8
303e742a1043dbd56fe11f0490cb74b7a738bab2238Christian König      ureg_MOV(shader, ureg_writemask(t_tc, TGSI_WRITEMASK_X), ureg_imm1f(shader, 1.0f / BLOCK_WIDTH * i));
30474c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König      fetch_four(shader, r, ureg_src(t_tc), sampler[1], start[1], block, true, true, matrix->width0);
305a984c67b316ac2ca9aaf6d38a3127cf3d61a249eChristian König#elif NR_RENDER_TARGETS == 1
30674c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König      fetch_four(shader, r, block, sampler[1], start[1], block, true, true, matrix->width0);
307a984c67b316ac2ca9aaf6d38a3127cf3d61a249eChristian König#else
308a984c67b316ac2ca9aaf6d38a3127cf3d61a249eChristian König#error invalid number of render targets
309a984c67b316ac2ca9aaf6d38a3127cf3d61a249eChristian König#endif
310a984c67b316ac2ca9aaf6d38a3127cf3d61a249eChristian König
31174c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König      for (j = 0; j < 4; ++j) {
31274c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König         matrix_mul(shader, ureg_writemask(fragment[i], TGSI_WRITEMASK_X << j), l[j], r);
31374c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König      }
314e742a1043dbd56fe11f0490cb74b7a738bab2238Christian König      ureg_release_temporary(shader, r[0]);
315e742a1043dbd56fe11f0490cb74b7a738bab2238Christian König      ureg_release_temporary(shader, r[1]);
316e742a1043dbd56fe11f0490cb74b7a738bab2238Christian König   }
31712836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König
31812836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König   ureg_release_temporary(shader, t_tc);
319cfe489b89723117e56674c2be7761c201f8d78ffChristian König   ureg_release_temporary(shader, tmp);
32074c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König
32174c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König   for (i = 0; i < 4; ++i) {
32274c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König      ureg_release_temporary(shader, l[i][0]);
32374c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König      ureg_release_temporary(shader, l[i][1]);
32474c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König   }
325508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
326508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   ureg_END(shader);
327508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
328508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   return ureg_create_shader_and_destroy(shader, idct->pipe);
329508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König}
330508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
33195febb69cc333dad75c0f2da19dd85f444281ad2Christian Königstatic void *
33295febb69cc333dad75c0f2da19dd85f444281ad2Christian Königcreate_empty_block_frag_shader(struct vl_idct *idct)
33395febb69cc333dad75c0f2da19dd85f444281ad2Christian König{
33495febb69cc333dad75c0f2da19dd85f444281ad2Christian König   struct ureg_program *shader;
33595febb69cc333dad75c0f2da19dd85f444281ad2Christian König   struct ureg_dst fragment;
33695febb69cc333dad75c0f2da19dd85f444281ad2Christian König
33795febb69cc333dad75c0f2da19dd85f444281ad2Christian König   shader = ureg_create(TGSI_PROCESSOR_FRAGMENT);
33895febb69cc333dad75c0f2da19dd85f444281ad2Christian König   if (!shader)
33995febb69cc333dad75c0f2da19dd85f444281ad2Christian König      return NULL;
34095febb69cc333dad75c0f2da19dd85f444281ad2Christian König
34195febb69cc333dad75c0f2da19dd85f444281ad2Christian König   fragment = ureg_DECL_output(shader, TGSI_SEMANTIC_COLOR, 0);
34295febb69cc333dad75c0f2da19dd85f444281ad2Christian König
34395febb69cc333dad75c0f2da19dd85f444281ad2Christian König   ureg_MOV(shader, fragment, ureg_imm1f(shader, 0.0f));
34495febb69cc333dad75c0f2da19dd85f444281ad2Christian König
34595febb69cc333dad75c0f2da19dd85f444281ad2Christian König   ureg_END(shader);
34695febb69cc333dad75c0f2da19dd85f444281ad2Christian König
34795febb69cc333dad75c0f2da19dd85f444281ad2Christian König   return ureg_create_shader_and_destroy(shader, idct->pipe);
34895febb69cc333dad75c0f2da19dd85f444281ad2Christian König}
34995febb69cc333dad75c0f2da19dd85f444281ad2Christian König
350508a4a056c3140dc1f90b93acd46c06c30f7094eChristian Königstatic bool
351508a4a056c3140dc1f90b93acd46c06c30f7094eChristian Königinit_shaders(struct vl_idct *idct)
352508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König{
353e742a1043dbd56fe11f0490cb74b7a738bab2238Christian König   idct->matrix_vs = create_vert_shader(idct, true);
3545a8078486a013152d150a4524ebfab929eefe6c4Christian König   idct->matrix_fs = create_matrix_frag_shader(idct);
35512836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König
356e742a1043dbd56fe11f0490cb74b7a738bab2238Christian König   idct->transpose_vs = create_vert_shader(idct, true);
35712836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König   idct->transpose_fs = create_transpose_frag_shader(idct);
35812836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König
359e742a1043dbd56fe11f0490cb74b7a738bab2238Christian König   idct->eb_vs = create_vert_shader(idct, false);
3605a8078486a013152d150a4524ebfab929eefe6c4Christian König   idct->eb_fs = create_empty_block_frag_shader(idct);
361508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
36221efda86875096333dc0412c0edab1e188f551d8Christian König   return
36312836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König      idct->transpose_vs != NULL && idct->transpose_fs != NULL &&
36412836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König      idct->matrix_vs != NULL && idct->matrix_fs != NULL &&
36512836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König      idct->eb_vs != NULL && idct->eb_fs != NULL;
366508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König}
367508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
368508a4a056c3140dc1f90b93acd46c06c30f7094eChristian Königstatic void
369508a4a056c3140dc1f90b93acd46c06c30f7094eChristian Königcleanup_shaders(struct vl_idct *idct)
370508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König{
37112836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König   idct->pipe->delete_vs_state(idct->pipe, idct->transpose_vs);
372508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   idct->pipe->delete_fs_state(idct->pipe, idct->transpose_fs);
37312836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König
37412836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König   idct->pipe->delete_vs_state(idct->pipe, idct->matrix_vs);
375508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   idct->pipe->delete_fs_state(idct->pipe, idct->matrix_fs);
37612836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König
37712836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König   idct->pipe->delete_vs_state(idct->pipe, idct->eb_vs);
37895febb69cc333dad75c0f2da19dd85f444281ad2Christian König   idct->pipe->delete_fs_state(idct->pipe, idct->eb_fs);
379508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König}
380508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
381508a4a056c3140dc1f90b93acd46c06c30f7094eChristian Königstatic bool
382508a4a056c3140dc1f90b93acd46c06c30f7094eChristian Königinit_buffers(struct vl_idct *idct)
383508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König{
384508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   struct pipe_resource template;
385508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   struct pipe_sampler_view sampler_view;
386508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   struct pipe_vertex_element vertex_elems[2];
38721efda86875096333dc0412c0edab1e188f551d8Christian König   unsigned i;
388508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
389508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   memset(&template, 0, sizeof(struct pipe_resource));
390508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   template.last_level = 0;
391508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   template.depth0 = 1;
392508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   template.bind = PIPE_BIND_SAMPLER_VIEW;
393508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   template.flags = 0;
394508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
395e742a1043dbd56fe11f0490cb74b7a738bab2238Christian König   template.target = PIPE_TEXTURE_2D;
39613e28cff7655adec0f89aed9c5ee74f8481133abChristian König   template.format = PIPE_FORMAT_R16G16B16A16_SNORM;
39712836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König   template.width0 = idct->destination->width0 / 4;
398508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   template.height0 = idct->destination->height0;
399e742a1043dbd56fe11f0490cb74b7a738bab2238Christian König   template.depth0 = 1;
40013e28cff7655adec0f89aed9c5ee74f8481133abChristian König   template.usage = PIPE_USAGE_STREAM;
401508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   idct->textures.individual.source = idct->pipe->screen->resource_create(idct->pipe->screen, &template);
402508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
403e742a1043dbd56fe11f0490cb74b7a738bab2238Christian König   template.target = PIPE_TEXTURE_3D;
40474c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König   template.format = PIPE_FORMAT_R16G16B16A16_SNORM;
405a984c67b316ac2ca9aaf6d38a3127cf3d61a249eChristian König   template.width0 = idct->destination->width0 / NR_RENDER_TARGETS;
40674c71f09f3d321963b738acfb0bfd30b1e1efaebChristian König   template.height0 = idct->destination->height0 / 4;
407a984c67b316ac2ca9aaf6d38a3127cf3d61a249eChristian König   template.depth0 = NR_RENDER_TARGETS;
40803c5a0ea5cd5b3e5931d6784749f87789a016b98Christian König   template.usage = PIPE_USAGE_STATIC;
409508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   idct->textures.individual.intermediate = idct->pipe->screen->resource_create(idct->pipe->screen, &template);
410508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
411508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   for (i = 0; i < 4; ++i) {
41221efda86875096333dc0412c0edab1e188f551d8Christian König      if(idct->textures.all[i] == NULL)
41321efda86875096333dc0412c0edab1e188f551d8Christian König         return false; /* a texture failed to allocate */
41421efda86875096333dc0412c0edab1e188f551d8Christian König
415508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König      u_sampler_view_default_template(&sampler_view, idct->textures.all[i], idct->textures.all[i]->format);
416508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König      idct->sampler_views.all[i] = idct->pipe->create_sampler_view(idct->pipe, idct->textures.all[i], &sampler_view);
417508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   }
418508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
4194abe7382882a451a7750ccc451b8568768d122cbChristian König   idct->vertex_bufs.individual.quad = vl_vb_upload_quads(idct->pipe, idct->max_blocks);
420508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
42121efda86875096333dc0412c0edab1e188f551d8Christian König   if(idct->vertex_bufs.individual.quad.buffer == NULL)
42221efda86875096333dc0412c0edab1e188f551d8Christian König      return false;
42321efda86875096333dc0412c0edab1e188f551d8Christian König
424e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König   idct->vertex_bufs.individual.pos.stride = sizeof(struct vertex2f);
42595febb69cc333dad75c0f2da19dd85f444281ad2Christian König   idct->vertex_bufs.individual.pos.max_index = 4 * idct->max_blocks - 1;
426e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König   idct->vertex_bufs.individual.pos.buffer_offset = 0;
427e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König   idct->vertex_bufs.individual.pos.buffer = pipe_buffer_create
428508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   (
429508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König      idct->pipe->screen,
430508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König      PIPE_BIND_VERTEX_BUFFER,
43195febb69cc333dad75c0f2da19dd85f444281ad2Christian König      sizeof(struct vertex2f) * 4 * idct->max_blocks
432508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   );
433508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
43421efda86875096333dc0412c0edab1e188f551d8Christian König   if(idct->vertex_bufs.individual.pos.buffer == NULL)
43521efda86875096333dc0412c0edab1e188f551d8Christian König      return false;
43621efda86875096333dc0412c0edab1e188f551d8Christian König
437508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   /* Rect element */
438508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   vertex_elems[0].src_offset = 0;
439508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   vertex_elems[0].instance_divisor = 0;
440508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   vertex_elems[0].vertex_buffer_index = 0;
441508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   vertex_elems[0].src_format = PIPE_FORMAT_R32G32_FLOAT;
442508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
443508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   /* Pos element */
444508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   vertex_elems[1].src_offset = 0;
445508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   vertex_elems[1].instance_divisor = 0;
446508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   vertex_elems[1].vertex_buffer_index = 1;
447508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   vertex_elems[1].src_format = PIPE_FORMAT_R32G32_FLOAT;
448508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
449508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   idct->vertex_elems_state = idct->pipe->create_vertex_elements_state(idct->pipe, 2, vertex_elems);
450508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
451508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   return true;
452508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König}
453508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
454508a4a056c3140dc1f90b93acd46c06c30f7094eChristian Königstatic void
455508a4a056c3140dc1f90b93acd46c06c30f7094eChristian Königcleanup_buffers(struct vl_idct *idct)
456508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König{
457508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   unsigned i;
458508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
459508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   assert(idct);
460508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
461508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   for (i = 0; i < 4; ++i) {
462508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König      pipe_sampler_view_reference(&idct->sampler_views.all[i], NULL);
463508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König      pipe_resource_reference(&idct->textures.all[i], NULL);
464508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   }
465508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
466508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   idct->pipe->delete_vertex_elements_state(idct->pipe, idct->vertex_elems_state);
467e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König   pipe_resource_reference(&idct->vertex_bufs.individual.quad.buffer, NULL);
468e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König   pipe_resource_reference(&idct->vertex_bufs.individual.pos.buffer, NULL);
469508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König}
470508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
471e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian Königstatic void
472e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian Königinit_state(struct vl_idct *idct)
473e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König{
474e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König   struct pipe_sampler_state sampler;
475e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König   unsigned i;
476e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König
47712836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König   idct->viewport[0].scale[0] = idct->textures.individual.intermediate->width0;
47812836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König   idct->viewport[0].scale[1] = idct->textures.individual.intermediate->height0;
47912836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König
480027704db75a61300e733b0f5a9efbb491189dce5Christian König   idct->viewport[1].scale[0] = idct->destination->width0;
48112836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König   idct->viewport[1].scale[1] = idct->destination->height0;
48212836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König
48312836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König   idct->fb_state[0].width = idct->textures.individual.intermediate->width0;
48412836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König   idct->fb_state[0].height = idct->textures.individual.intermediate->height0;
485508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
486a984c67b316ac2ca9aaf6d38a3127cf3d61a249eChristian König   idct->fb_state[0].nr_cbufs = NR_RENDER_TARGETS;
487a984c67b316ac2ca9aaf6d38a3127cf3d61a249eChristian König   for(i = 0; i < NR_RENDER_TARGETS; ++i) {
488e742a1043dbd56fe11f0490cb74b7a738bab2238Christian König      idct->fb_state[0].cbufs[i] = idct->pipe->screen->get_tex_surface(
489e742a1043dbd56fe11f0490cb74b7a738bab2238Christian König         idct->pipe->screen, idct->textures.individual.intermediate, 0, 0, i,
490e742a1043dbd56fe11f0490cb74b7a738bab2238Christian König         PIPE_BIND_SAMPLER_VIEW | PIPE_BIND_RENDER_TARGET);
491e742a1043dbd56fe11f0490cb74b7a738bab2238Christian König   }
492e742a1043dbd56fe11f0490cb74b7a738bab2238Christian König
493027704db75a61300e733b0f5a9efbb491189dce5Christian König   idct->fb_state[1].width = idct->destination->width0;
49412836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König   idct->fb_state[1].height = idct->destination->height0;
495027704db75a61300e733b0f5a9efbb491189dce5Christian König
496e742a1043dbd56fe11f0490cb74b7a738bab2238Christian König   idct->fb_state[1].nr_cbufs = 1;
497e742a1043dbd56fe11f0490cb74b7a738bab2238Christian König   idct->fb_state[1].cbufs[0] = idct->pipe->screen->get_tex_surface(
498e742a1043dbd56fe11f0490cb74b7a738bab2238Christian König      idct->pipe->screen, idct->destination, 0, 0, 0,
499e742a1043dbd56fe11f0490cb74b7a738bab2238Christian König      PIPE_BIND_SAMPLER_VIEW | PIPE_BIND_RENDER_TARGET);
500e742a1043dbd56fe11f0490cb74b7a738bab2238Christian König
501027704db75a61300e733b0f5a9efbb491189dce5Christian König   for(i = 0; i < 2; ++i) {
502027704db75a61300e733b0f5a9efbb491189dce5Christian König      idct->viewport[i].scale[2] = 1;
503027704db75a61300e733b0f5a9efbb491189dce5Christian König      idct->viewport[i].scale[3] = 1;
504027704db75a61300e733b0f5a9efbb491189dce5Christian König      idct->viewport[i].translate[0] = 0;
505027704db75a61300e733b0f5a9efbb491189dce5Christian König      idct->viewport[i].translate[1] = 0;
506027704db75a61300e733b0f5a9efbb491189dce5Christian König      idct->viewport[i].translate[2] = 0;
507027704db75a61300e733b0f5a9efbb491189dce5Christian König      idct->viewport[i].translate[3] = 0;
508027704db75a61300e733b0f5a9efbb491189dce5Christian König
509027704db75a61300e733b0f5a9efbb491189dce5Christian König      idct->fb_state[i].zsbuf = NULL;
510027704db75a61300e733b0f5a9efbb491189dce5Christian König   }
511508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
512e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König   for (i = 0; i < 4; ++i) {
513e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König      memset(&sampler, 0, sizeof(sampler));
514e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König      sampler.wrap_s = PIPE_TEX_WRAP_CLAMP_TO_EDGE;
515e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König      sampler.wrap_t = PIPE_TEX_WRAP_CLAMP_TO_EDGE;
516e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König      sampler.wrap_r = PIPE_TEX_WRAP_CLAMP_TO_EDGE;
517e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König      sampler.min_img_filter = PIPE_TEX_FILTER_NEAREST;
518e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König      sampler.min_mip_filter = PIPE_TEX_MIPFILTER_NONE;
519e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König      sampler.mag_img_filter = PIPE_TEX_FILTER_NEAREST;
520e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König      sampler.compare_mode = PIPE_TEX_COMPARE_NONE;
521e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König      sampler.compare_func = PIPE_FUNC_ALWAYS;
522e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König      sampler.normalized_coords = 1;
523e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König      /*sampler.shadow_ambient = ; */
524e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König      /*sampler.lod_bias = ; */
525e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König      sampler.min_lod = 0;
526e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König      /*sampler.max_lod = ; */
527e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König      /*sampler.border_color[0] = ; */
528e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König      /*sampler.max_anisotropy = ; */
529e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König      idct->samplers.all[i] = idct->pipe->create_sampler_state(idct->pipe, &sampler);
530e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König   }
531e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König}
532e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König
533e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian Königstatic void
534e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian Königcleanup_state(struct vl_idct *idct)
535e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König{
536e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König   unsigned i;
537e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König
538a984c67b316ac2ca9aaf6d38a3127cf3d61a249eChristian König   for(i = 0; i < NR_RENDER_TARGETS; ++i) {
539e742a1043dbd56fe11f0490cb74b7a738bab2238Christian König      idct->pipe->screen->tex_surface_destroy(idct->fb_state[0].cbufs[i]);
540e742a1043dbd56fe11f0490cb74b7a738bab2238Christian König   }
541e742a1043dbd56fe11f0490cb74b7a738bab2238Christian König
542e742a1043dbd56fe11f0490cb74b7a738bab2238Christian König   idct->pipe->screen->tex_surface_destroy(idct->fb_state[1].cbufs[0]);
543e742a1043dbd56fe11f0490cb74b7a738bab2238Christian König
544e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König   for (i = 0; i < 4; ++i)
545e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König      idct->pipe->delete_sampler_state(idct->pipe, idct->samplers.all[i]);
546e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König}
547e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König
5483dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian Königstruct pipe_resource *
5493dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian Königvl_idct_upload_matrix(struct pipe_context *pipe)
5503dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König{
5513dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König   struct pipe_resource template, *matrix;
5523dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König   struct pipe_transfer *buf_transfer;
5533dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König   unsigned i, j, pitch;
5543dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König   float *f;
5553dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König
5563dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König   struct pipe_box rect =
5573dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König   {
5583dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König      0, 0, 0,
5593dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König      BLOCK_WIDTH,
5603dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König      BLOCK_HEIGHT,
5613dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König      1
5623dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König   };
5633dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König
5643dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König   memset(&template, 0, sizeof(struct pipe_resource));
5653dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König   template.target = PIPE_TEXTURE_2D;
5663dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König   template.format = PIPE_FORMAT_R32G32B32A32_FLOAT;
5673dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König   template.last_level = 0;
5683dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König   template.width0 = 2;
5693dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König   template.height0 = 8;
5703dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König   template.depth0 = 1;
5713dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König   template.usage = PIPE_USAGE_IMMUTABLE;
5723dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König   template.bind = PIPE_BIND_SAMPLER_VIEW;
5733dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König   template.flags = 0;
5743dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König
5753dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König   matrix = pipe->screen->resource_create(pipe->screen, &template);
5763dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König
5773dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König   /* matrix */
5783dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König   buf_transfer = pipe->get_transfer
5793dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König   (
5803dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König      pipe, matrix,
5813dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König      u_subresource(0, 0),
5823dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König      PIPE_TRANSFER_WRITE | PIPE_TRANSFER_DISCARD,
5833dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König      &rect
5843dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König   );
5853fd53e6c2a05e65872de4292557d7839cbcf7395Christian König   pitch = buf_transfer->stride / sizeof(float);
5863dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König
5873dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König   f = pipe->transfer_map(pipe, buf_transfer);
5883dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König   for(i = 0; i < BLOCK_HEIGHT; ++i)
5893dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König      for(j = 0; j < BLOCK_WIDTH; ++j)
5903fd53e6c2a05e65872de4292557d7839cbcf7395Christian König         f[i * pitch + j] = const_matrix[j][i]; // transpose
5913dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König
5923dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König   pipe->transfer_unmap(pipe, buf_transfer);
5933dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König   pipe->transfer_destroy(pipe, buf_transfer);
5943dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König
5953dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König   return matrix;
5963dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König}
5973dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König
598336c7735ae97ddc0a177562375136297c2de3d19Christian Königstatic void
599336c7735ae97ddc0a177562375136297c2de3d19Christian Königxfer_buffers_map(struct vl_idct *idct)
600336c7735ae97ddc0a177562375136297c2de3d19Christian König{
601336c7735ae97ddc0a177562375136297c2de3d19Christian König   struct pipe_box rect =
602336c7735ae97ddc0a177562375136297c2de3d19Christian König   {
603336c7735ae97ddc0a177562375136297c2de3d19Christian König      0, 0, 0,
604336c7735ae97ddc0a177562375136297c2de3d19Christian König      idct->textures.individual.source->width0,
605336c7735ae97ddc0a177562375136297c2de3d19Christian König      idct->textures.individual.source->height0,
606336c7735ae97ddc0a177562375136297c2de3d19Christian König      1
607336c7735ae97ddc0a177562375136297c2de3d19Christian König   };
608336c7735ae97ddc0a177562375136297c2de3d19Christian König
609336c7735ae97ddc0a177562375136297c2de3d19Christian König   idct->tex_transfer = idct->pipe->get_transfer
610336c7735ae97ddc0a177562375136297c2de3d19Christian König   (
611336c7735ae97ddc0a177562375136297c2de3d19Christian König      idct->pipe, idct->textures.individual.source,
612336c7735ae97ddc0a177562375136297c2de3d19Christian König      u_subresource(0, 0),
613336c7735ae97ddc0a177562375136297c2de3d19Christian König      PIPE_TRANSFER_WRITE | PIPE_TRANSFER_DISCARD,
614336c7735ae97ddc0a177562375136297c2de3d19Christian König      &rect
615336c7735ae97ddc0a177562375136297c2de3d19Christian König   );
616336c7735ae97ddc0a177562375136297c2de3d19Christian König
617336c7735ae97ddc0a177562375136297c2de3d19Christian König   idct->texels = idct->pipe->transfer_map(idct->pipe, idct->tex_transfer);
618336c7735ae97ddc0a177562375136297c2de3d19Christian König}
619336c7735ae97ddc0a177562375136297c2de3d19Christian König
620336c7735ae97ddc0a177562375136297c2de3d19Christian Königstatic void
621336c7735ae97ddc0a177562375136297c2de3d19Christian Königxfer_buffers_unmap(struct vl_idct *idct)
622336c7735ae97ddc0a177562375136297c2de3d19Christian König{
623336c7735ae97ddc0a177562375136297c2de3d19Christian König   idct->pipe->transfer_unmap(idct->pipe, idct->tex_transfer);
624336c7735ae97ddc0a177562375136297c2de3d19Christian König   idct->pipe->transfer_destroy(idct->pipe, idct->tex_transfer);
625336c7735ae97ddc0a177562375136297c2de3d19Christian König}
626336c7735ae97ddc0a177562375136297c2de3d19Christian König
62703c5a0ea5cd5b3e5931d6784749f87789a016b98Christian Königbool
6283dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian Königvl_idct_init(struct vl_idct *idct, struct pipe_context *pipe, struct pipe_resource *dst, struct pipe_resource *matrix)
629e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König{
630e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König   assert(idct && pipe && dst);
631e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König
632e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König   idct->pipe = pipe;
6333dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König   pipe_resource_reference(&idct->textures.individual.matrix, matrix);
6343dd7bf7d39781f3ef4c0b53732945674c9924cdfChristian König   pipe_resource_reference(&idct->textures.individual.transpose, matrix);
635508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   pipe_resource_reference(&idct->destination, dst);
636508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
6374abe7382882a451a7750ccc451b8568768d122cbChristian König   idct->max_blocks =
6384abe7382882a451a7750ccc451b8568768d122cbChristian König      align(idct->destination->width0, BLOCK_WIDTH) / BLOCK_WIDTH *
6394abe7382882a451a7750ccc451b8568768d122cbChristian König      align(idct->destination->height0, BLOCK_HEIGHT) / BLOCK_HEIGHT *
6404abe7382882a451a7750ccc451b8568768d122cbChristian König      idct->destination->depth0;
6414abe7382882a451a7750ccc451b8568768d122cbChristian König
64212836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König   if(!init_buffers(idct))
643508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König      return false;
644508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
64512836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König   if(!init_shaders(idct)) {
64612836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König      cleanup_buffers(idct);
647508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König      return false;
648508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   }
649508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
6504abe7382882a451a7750ccc451b8568768d122cbChristian König   if(!vl_vb_init(&idct->blocks, idct->max_blocks)) {
6514abe7382882a451a7750ccc451b8568768d122cbChristian König      cleanup_shaders(idct);
6524abe7382882a451a7750ccc451b8568768d122cbChristian König      cleanup_buffers(idct);
6534abe7382882a451a7750ccc451b8568768d122cbChristian König      return false;
6544abe7382882a451a7750ccc451b8568768d122cbChristian König   }
6554abe7382882a451a7750ccc451b8568768d122cbChristian König
6564abe7382882a451a7750ccc451b8568768d122cbChristian König   if(!vl_vb_init(&idct->empty_blocks, idct->max_blocks)) {
6574abe7382882a451a7750ccc451b8568768d122cbChristian König      vl_vb_cleanup(&idct->blocks);
6584abe7382882a451a7750ccc451b8568768d122cbChristian König      cleanup_shaders(idct);
6594abe7382882a451a7750ccc451b8568768d122cbChristian König      cleanup_buffers(idct);
6604abe7382882a451a7750ccc451b8568768d122cbChristian König      return false;
6614abe7382882a451a7750ccc451b8568768d122cbChristian König   }
6624abe7382882a451a7750ccc451b8568768d122cbChristian König
66312836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König   init_state(idct);
66412836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König
665508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   xfer_buffers_map(idct);
666508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
667508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   return true;
668508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König}
669508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
67003c5a0ea5cd5b3e5931d6784749f87789a016b98Christian Königvoid
67103c5a0ea5cd5b3e5931d6784749f87789a016b98Christian Königvl_idct_cleanup(struct vl_idct *idct)
672508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König{
6734abe7382882a451a7750ccc451b8568768d122cbChristian König   vl_vb_cleanup(&idct->blocks);
6744abe7382882a451a7750ccc451b8568768d122cbChristian König   vl_vb_cleanup(&idct->empty_blocks);
675508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   cleanup_shaders(idct);
676508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   cleanup_buffers(idct);
677e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König
678e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König   cleanup_state(idct);
679e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König
680e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König   pipe_resource_reference(&idct->destination, NULL);
681508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König}
682508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
68303c5a0ea5cd5b3e5931d6784749f87789a016b98Christian Königvoid
68403c5a0ea5cd5b3e5931d6784749f87789a016b98Christian Königvl_idct_add_block(struct vl_idct *idct, unsigned x, unsigned y, short *block)
685508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König{
686508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   unsigned tex_pitch;
687508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   short *texels;
688e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König
689508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   unsigned i;
690508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
691508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   assert(idct);
692e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König
69303c5a0ea5cd5b3e5931d6784749f87789a016b98Christian König   if(block) {
69412836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König      tex_pitch = idct->tex_transfer->stride / sizeof(short);
69512836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König      texels = idct->texels + y * tex_pitch * BLOCK_HEIGHT + x * BLOCK_WIDTH;
69603c5a0ea5cd5b3e5931d6784749f87789a016b98Christian König
69703c5a0ea5cd5b3e5931d6784749f87789a016b98Christian König      for (i = 0; i < BLOCK_HEIGHT; ++i)
69812836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König         memcpy(texels + i * tex_pitch, block + i * BLOCK_WIDTH, BLOCK_WIDTH * sizeof(short));
699e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König
7004abe7382882a451a7750ccc451b8568768d122cbChristian König      vl_vb_add_block(&idct->blocks, false, x, y);
701336c7735ae97ddc0a177562375136297c2de3d19Christian König   } else {
70295febb69cc333dad75c0f2da19dd85f444281ad2Christian König
7034abe7382882a451a7750ccc451b8568768d122cbChristian König      vl_vb_add_block(&idct->empty_blocks, true, x, y);
70403c5a0ea5cd5b3e5931d6784749f87789a016b98Christian König   }
705508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König}
706508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König
70703c5a0ea5cd5b3e5931d6784749f87789a016b98Christian Königvoid
70803c5a0ea5cd5b3e5931d6784749f87789a016b98Christian Königvl_idct_flush(struct vl_idct *idct)
709508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König{
7104abe7382882a451a7750ccc451b8568768d122cbChristian König   struct pipe_transfer *vec_transfer;
7114abe7382882a451a7750ccc451b8568768d122cbChristian König   struct quadf *vectors;
7124abe7382882a451a7750ccc451b8568768d122cbChristian König   unsigned num_blocks, num_empty_blocks;
7134abe7382882a451a7750ccc451b8568768d122cbChristian König
7144abe7382882a451a7750ccc451b8568768d122cbChristian König   assert(idct);
7154abe7382882a451a7750ccc451b8568768d122cbChristian König
7164abe7382882a451a7750ccc451b8568768d122cbChristian König   vectors = pipe_buffer_map
7174abe7382882a451a7750ccc451b8568768d122cbChristian König   (
7184abe7382882a451a7750ccc451b8568768d122cbChristian König      idct->pipe,
7194abe7382882a451a7750ccc451b8568768d122cbChristian König      idct->vertex_bufs.individual.pos.buffer,
7204abe7382882a451a7750ccc451b8568768d122cbChristian König      PIPE_TRANSFER_WRITE | PIPE_TRANSFER_DISCARD,
7214abe7382882a451a7750ccc451b8568768d122cbChristian König      &vec_transfer
7224abe7382882a451a7750ccc451b8568768d122cbChristian König   );
7234abe7382882a451a7750ccc451b8568768d122cbChristian König
7244abe7382882a451a7750ccc451b8568768d122cbChristian König   num_blocks = vl_vb_upload(&idct->blocks, vectors);
7254abe7382882a451a7750ccc451b8568768d122cbChristian König   num_empty_blocks = vl_vb_upload(&idct->empty_blocks, vectors + num_blocks);
7264abe7382882a451a7750ccc451b8568768d122cbChristian König
7274abe7382882a451a7750ccc451b8568768d122cbChristian König   pipe_buffer_unmap(idct->pipe, idct->vertex_bufs.individual.pos.buffer, vec_transfer);
7284abe7382882a451a7750ccc451b8568768d122cbChristian König
729508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   xfer_buffers_unmap(idct);
730e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König
7314abe7382882a451a7750ccc451b8568768d122cbChristian König   if(num_blocks > 0) {
73203c5a0ea5cd5b3e5931d6784749f87789a016b98Christian König
73303c5a0ea5cd5b3e5931d6784749f87789a016b98Christian König      /* first stage */
734027704db75a61300e733b0f5a9efbb491189dce5Christian König      idct->pipe->set_framebuffer_state(idct->pipe, &idct->fb_state[0]);
735027704db75a61300e733b0f5a9efbb491189dce5Christian König      idct->pipe->set_viewport_state(idct->pipe, &idct->viewport[0]);
73603c5a0ea5cd5b3e5931d6784749f87789a016b98Christian König
73703c5a0ea5cd5b3e5931d6784749f87789a016b98Christian König      idct->pipe->set_vertex_buffers(idct->pipe, 2, idct->vertex_bufs.all);
73803c5a0ea5cd5b3e5931d6784749f87789a016b98Christian König      idct->pipe->bind_vertex_elements_state(idct->pipe, idct->vertex_elems_state);
7392c9db2484b7c1cec7a3a629f70a5aa840e16268eChristian König      idct->pipe->set_fragment_sampler_views(idct->pipe, 2, idct->sampler_views.stage[0]);
7402c9db2484b7c1cec7a3a629f70a5aa840e16268eChristian König      idct->pipe->bind_fragment_sampler_states(idct->pipe, 2, idct->samplers.stage[0]);
74112836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König      idct->pipe->bind_vs_state(idct->pipe, idct->matrix_vs);
74213e28cff7655adec0f89aed9c5ee74f8481133abChristian König      idct->pipe->bind_fs_state(idct->pipe, idct->matrix_fs);
74303c5a0ea5cd5b3e5931d6784749f87789a016b98Christian König
7444abe7382882a451a7750ccc451b8568768d122cbChristian König      util_draw_arrays(idct->pipe, PIPE_PRIM_QUADS, 0, num_blocks * 4);
74503c5a0ea5cd5b3e5931d6784749f87789a016b98Christian König
74603c5a0ea5cd5b3e5931d6784749f87789a016b98Christian König      /* second stage */
747027704db75a61300e733b0f5a9efbb491189dce5Christian König      idct->pipe->set_framebuffer_state(idct->pipe, &idct->fb_state[1]);
748027704db75a61300e733b0f5a9efbb491189dce5Christian König      idct->pipe->set_viewport_state(idct->pipe, &idct->viewport[1]);
74903c5a0ea5cd5b3e5931d6784749f87789a016b98Christian König
75003c5a0ea5cd5b3e5931d6784749f87789a016b98Christian König      idct->pipe->set_vertex_buffers(idct->pipe, 2, idct->vertex_bufs.all);
75103c5a0ea5cd5b3e5931d6784749f87789a016b98Christian König      idct->pipe->bind_vertex_elements_state(idct->pipe, idct->vertex_elems_state);
7522c9db2484b7c1cec7a3a629f70a5aa840e16268eChristian König      idct->pipe->set_fragment_sampler_views(idct->pipe, 2, idct->sampler_views.stage[1]);
7532c9db2484b7c1cec7a3a629f70a5aa840e16268eChristian König      idct->pipe->bind_fragment_sampler_states(idct->pipe, 2, idct->samplers.stage[1]);
75412836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König      idct->pipe->bind_vs_state(idct->pipe, idct->transpose_vs);
75513e28cff7655adec0f89aed9c5ee74f8481133abChristian König      idct->pipe->bind_fs_state(idct->pipe, idct->transpose_fs);
75603c5a0ea5cd5b3e5931d6784749f87789a016b98Christian König
7574abe7382882a451a7750ccc451b8568768d122cbChristian König      util_draw_arrays(idct->pipe, PIPE_PRIM_QUADS, 0, num_blocks * 4);
75895febb69cc333dad75c0f2da19dd85f444281ad2Christian König   }
75903c5a0ea5cd5b3e5931d6784749f87789a016b98Christian König
7604abe7382882a451a7750ccc451b8568768d122cbChristian König   if(num_empty_blocks > 0) {
76195febb69cc333dad75c0f2da19dd85f444281ad2Christian König
76295febb69cc333dad75c0f2da19dd85f444281ad2Christian König      /* empty block handling */
763027704db75a61300e733b0f5a9efbb491189dce5Christian König      idct->pipe->set_framebuffer_state(idct->pipe, &idct->fb_state[1]);
764027704db75a61300e733b0f5a9efbb491189dce5Christian König      idct->pipe->set_viewport_state(idct->pipe, &idct->viewport[1]);
76595febb69cc333dad75c0f2da19dd85f444281ad2Christian König
76695febb69cc333dad75c0f2da19dd85f444281ad2Christian König      idct->pipe->set_vertex_buffers(idct->pipe, 2, idct->vertex_bufs.all);
76795febb69cc333dad75c0f2da19dd85f444281ad2Christian König      idct->pipe->bind_vertex_elements_state(idct->pipe, idct->vertex_elems_state);
76812836fbcfad7f317b1f5aa5e46f9946894bf040cChristian König      idct->pipe->bind_vs_state(idct->pipe, idct->eb_vs);
76995febb69cc333dad75c0f2da19dd85f444281ad2Christian König      idct->pipe->bind_fs_state(idct->pipe, idct->eb_fs);
77095febb69cc333dad75c0f2da19dd85f444281ad2Christian König
7714abe7382882a451a7750ccc451b8568768d122cbChristian König      util_draw_arrays(idct->pipe, PIPE_PRIM_QUADS, num_blocks * 4, num_empty_blocks * 4);
77203c5a0ea5cd5b3e5931d6784749f87789a016b98Christian König   }
773e639e1b83ea65985cd84d12dc120d77cab80ba9eChristian König
774508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König   xfer_buffers_map(idct);
775508a4a056c3140dc1f90b93acd46c06c30f7094eChristian König}
776