From 8c0ccce30038f5d28e74f7f4b5b5c0bbd8ac6dbe Mon Sep 17 00:00:00 2001 From: Dave Airlie Date: Sat, 3 Nov 2012 20:49:35 +1000 Subject: [PATCH] st/mesa: add support for ARB_texture_cube_map_array (v2) This adds mesa state tracker support for the new extension, along with glsl->tgsi conversion to use the new opcodes where appropriate. v2: fix assert found running textureSize tests. Reviewed-by: Brian Paul Signed-off-by: Dave Airlie --- src/mesa/state_tracker/st_cb_texture.c | 5 ++ src/mesa/state_tracker/st_extensions.c | 3 +- src/mesa/state_tracker/st_glsl_to_tgsi.cpp | 67 +++++++++++++++------- src/mesa/state_tracker/st_mesa_to_tgsi.c | 2 + src/mesa/state_tracker/st_texture.c | 10 +++- 5 files changed, 64 insertions(+), 23 deletions(-) diff --git a/src/mesa/state_tracker/st_cb_texture.c b/src/mesa/state_tracker/st_cb_texture.c index 6c287b3d482..b2711c3420f 100644 --- a/src/mesa/state_tracker/st_cb_texture.c +++ b/src/mesa/state_tracker/st_cb_texture.c @@ -102,6 +102,9 @@ gl_target_to_pipe(GLenum target) return PIPE_TEXTURE_2D_ARRAY; case GL_TEXTURE_BUFFER: return PIPE_BUFFER; + case GL_TEXTURE_CUBE_MAP_ARRAY: + case GL_PROXY_TEXTURE_CUBE_MAP_ARRAY: + return PIPE_TEXTURE_CUBE_ARRAY; default: assert(0); return 0; @@ -272,6 +275,7 @@ get_texture_dims(GLenum target) case GL_TEXTURE_EXTERNAL_OES: return 2; case GL_TEXTURE_3D: + case GL_TEXTURE_CUBE_MAP_ARRAY: return 3; default: assert(0 && "invalid texture target in get_texture_dims()"); @@ -1123,6 +1127,7 @@ copy_image_data_to_texture(struct st_context *st, assert(stImage->pt->target == PIPE_TEXTURE_1D_ARRAY || u_minify(stImage->pt->height0, src_level) == stImage->base.Height); assert(stImage->pt->target == PIPE_TEXTURE_2D_ARRAY || + stImage->pt->target == PIPE_TEXTURE_CUBE_ARRAY || u_minify(stImage->pt->depth0, src_level) == stImage->base.Depth); st_texture_image_copy(st->pipe, diff --git a/src/mesa/state_tracker/st_extensions.c b/src/mesa/state_tracker/st_extensions.c index 88770056830..7570d689494 100644 --- a/src/mesa/state_tracker/st_extensions.c +++ b/src/mesa/state_tracker/st_extensions.c @@ -378,7 +378,8 @@ void st_init_extensions(struct st_context *st) * support the GL_POINT_SPRITE_R_MODE_NV option. */ { o(MESA_texture_array), PIPE_CAP_MAX_TEXTURE_ARRAY_LAYERS }, - { o(OES_standard_derivatives), PIPE_CAP_SM3 } + { o(OES_standard_derivatives), PIPE_CAP_SM3 }, + { o(ARB_texture_cube_map_array), PIPE_CAP_CUBE_MAP_ARRAY } }; /* Required: render target and sampler support */ diff --git a/src/mesa/state_tracker/st_glsl_to_tgsi.cpp b/src/mesa/state_tracker/st_glsl_to_tgsi.cpp index cd47adc0486..c030a6b372e 100644 --- a/src/mesa/state_tracker/st_glsl_to_tgsi.cpp +++ b/src/mesa/state_tracker/st_glsl_to_tgsi.cpp @@ -2565,10 +2565,18 @@ glsl_to_tgsi_visitor::visit(ir_call *ir) void glsl_to_tgsi_visitor::visit(ir_texture *ir) { - st_src_reg result_src, coord, lod_info, projector, dx, dy, offset; - st_dst_reg result_dst, coord_dst; + st_src_reg result_src, coord, cube_sc, lod_info, projector, dx, dy, offset; + st_dst_reg result_dst, coord_dst, cube_sc_dst; glsl_to_tgsi_instruction *inst = NULL; unsigned opcode = TGSI_OPCODE_NOP; + const glsl_type *sampler_type = ir->sampler->type; + bool is_cube_array = false; + + /* if we are a cube array sampler */ + if ((sampler_type->sampler_dimensionality == GLSL_SAMPLER_DIM_CUBE && + sampler_type->sampler_array)) { + is_cube_array = true; + } if (ir->coordinate) { ir->coordinate->accept(this); @@ -2596,15 +2604,15 @@ glsl_to_tgsi_visitor::visit(ir_texture *ir) switch (ir->op) { case ir_tex: - opcode = TGSI_OPCODE_TEX; + opcode = (is_cube_array && ir->shadow_comparitor) ? TGSI_OPCODE_TEX2 : TGSI_OPCODE_TEX; break; case ir_txb: - opcode = TGSI_OPCODE_TXB; + opcode = is_cube_array ? TGSI_OPCODE_TXB2 : TGSI_OPCODE_TXB; ir->lod_info.bias->accept(this); lod_info = this->result; break; case ir_txl: - opcode = TGSI_OPCODE_TXL; + opcode = is_cube_array ? TGSI_OPCODE_TXL2 : TGSI_OPCODE_TXL; ir->lod_info.lod->accept(this); lod_info = this->result; break; @@ -2631,8 +2639,6 @@ glsl_to_tgsi_visitor::visit(ir_texture *ir) break; } - const glsl_type *sampler_type = ir->sampler->type; - if (ir->projector) { if (opcode == TGSI_OPCODE_TEX) { /* Slot the projector in as the last component of the coord. */ @@ -2692,17 +2698,25 @@ glsl_to_tgsi_visitor::visit(ir_texture *ir) */ ir->shadow_comparitor->accept(this); - /* XXX This will need to be updated for cubemap array samplers. */ - if ((sampler_type->sampler_dimensionality == GLSL_SAMPLER_DIM_2D && - sampler_type->sampler_array) || - sampler_type->sampler_dimensionality == GLSL_SAMPLER_DIM_CUBE) { - coord_dst.writemask = WRITEMASK_W; - } else { - coord_dst.writemask = WRITEMASK_Z; + if (is_cube_array) { + cube_sc = get_temp(glsl_type::float_type); + cube_sc_dst = st_dst_reg(cube_sc); + cube_sc_dst.writemask = WRITEMASK_X; + emit(ir, TGSI_OPCODE_MOV, cube_sc_dst, this->result); + cube_sc_dst.writemask = WRITEMASK_X; + } + else { + if ((sampler_type->sampler_dimensionality == GLSL_SAMPLER_DIM_2D && + sampler_type->sampler_array) || + sampler_type->sampler_dimensionality == GLSL_SAMPLER_DIM_CUBE) { + coord_dst.writemask = WRITEMASK_W; + } else { + coord_dst.writemask = WRITEMASK_Z; + } + + emit(ir, TGSI_OPCODE_MOV, coord_dst, this->result); + coord_dst.writemask = WRITEMASK_XYZW; } - - emit(ir, TGSI_OPCODE_MOV, coord_dst, this->result); - coord_dst.writemask = WRITEMASK_XYZW; } if (opcode == TGSI_OPCODE_TXL || opcode == TGSI_OPCODE_TXB || @@ -2719,7 +2733,11 @@ glsl_to_tgsi_visitor::visit(ir_texture *ir) inst = emit(ir, opcode, result_dst, lod_info); else if (opcode == TGSI_OPCODE_TXF) { inst = emit(ir, opcode, result_dst, coord); - } else + } else if (opcode == TGSI_OPCODE_TXL2 || opcode == TGSI_OPCODE_TXB2) { + inst = emit(ir, opcode, result_dst, coord, lod_info); + } else if (opcode == TGSI_OPCODE_TEX2) { + inst = emit(ir, opcode, result_dst, coord, cube_sc); + } else inst = emit(ir, opcode, result_dst, coord); if (ir->shadow_comparitor) @@ -2751,7 +2769,8 @@ glsl_to_tgsi_visitor::visit(ir_texture *ir) inst->tex_target = TEXTURE_3D_INDEX; break; case GLSL_SAMPLER_DIM_CUBE: - inst->tex_target = TEXTURE_CUBE_INDEX; + inst->tex_target = (sampler_type->sampler_array) + ? TEXTURE_CUBE_ARRAY_INDEX : TEXTURE_CUBE_INDEX; break; case GLSL_SAMPLER_DIM_RECT: inst->tex_target = TEXTURE_RECT_INDEX; @@ -4209,6 +4228,7 @@ compile_tgsi_instruction(struct st_translate *t, unsigned num_dst; unsigned num_src; + unsigned tex_target; num_dst = num_inst_dst_regs(inst->op); num_src = num_inst_src_regs(inst->op); @@ -4243,14 +4263,19 @@ compile_tgsi_instruction(struct st_translate *t, case TGSI_OPCODE_TXP: case TGSI_OPCODE_TXQ: case TGSI_OPCODE_TXF: + case TGSI_OPCODE_TEX2: + case TGSI_OPCODE_TXB2: + case TGSI_OPCODE_TXL2: src[num_src++] = t->samplers[inst->sampler]; for (i = 0; i < inst->tex_offset_num_offset; i++) { texoffsets[i] = translate_tex_offset(t, &inst->tex_offsets[i]); } + tex_target = st_translate_texture_target(inst->tex_target, inst->tex_shadow); + ureg_tex_insn(ureg, inst->op, - dst, num_dst, - st_translate_texture_target(inst->tex_target, inst->tex_shadow), + dst, num_dst, + tex_target, texoffsets, inst->tex_offset_num_offset, src, num_src); return; diff --git a/src/mesa/state_tracker/st_mesa_to_tgsi.c b/src/mesa/state_tracker/st_mesa_to_tgsi.c index 0822be7571c..81a870f8685 100644 --- a/src/mesa/state_tracker/st_mesa_to_tgsi.c +++ b/src/mesa/state_tracker/st_mesa_to_tgsi.c @@ -263,6 +263,7 @@ st_translate_texture_target( GLuint textarget, case TEXTURE_1D_ARRAY_INDEX: return TGSI_TEXTURE_SHADOW1D_ARRAY; case TEXTURE_2D_ARRAY_INDEX: return TGSI_TEXTURE_SHADOW2D_ARRAY; case TEXTURE_CUBE_INDEX: return TGSI_TEXTURE_SHADOWCUBE; + case TEXTURE_CUBE_ARRAY_INDEX: return TGSI_TEXTURE_SHADOWCUBE_ARRAY; default: break; } } @@ -272,6 +273,7 @@ st_translate_texture_target( GLuint textarget, case TEXTURE_2D_INDEX: return TGSI_TEXTURE_2D; case TEXTURE_3D_INDEX: return TGSI_TEXTURE_3D; case TEXTURE_CUBE_INDEX: return TGSI_TEXTURE_CUBE; + case TEXTURE_CUBE_ARRAY_INDEX: return TGSI_TEXTURE_CUBE_ARRAY; case TEXTURE_RECT_INDEX: return TGSI_TEXTURE_RECT; case TEXTURE_1D_ARRAY_INDEX: return TGSI_TEXTURE_1D_ARRAY; case TEXTURE_2D_ARRAY_INDEX: return TGSI_TEXTURE_2D_ARRAY; diff --git a/src/mesa/state_tracker/st_texture.c b/src/mesa/state_tracker/st_texture.c index d6dbf8d6cf6..5a4dcaab229 100644 --- a/src/mesa/state_tracker/st_texture.c +++ b/src/mesa/state_tracker/st_texture.c @@ -165,6 +165,13 @@ st_gl_texture_dims_to_pipe_dims(GLenum texture, *depthOut = 1; *layersOut = depthIn; break; + case GL_TEXTURE_CUBE_MAP_ARRAY: + case GL_PROXY_TEXTURE_CUBE_MAP_ARRAY: + *widthOut = widthIn; + *heightOut = heightIn; + *depthOut = 1; + *layersOut = depthIn; + break; default: assert(0 && "Unexpected texture in st_gl_texture_dims_to_pipe_dims()"); /* fall-through */ @@ -277,7 +284,8 @@ st_texture_image_data(struct st_context *st, GLuint layers; if (dst->target == PIPE_TEXTURE_1D_ARRAY || - dst->target == PIPE_TEXTURE_2D_ARRAY) + dst->target == PIPE_TEXTURE_2D_ARRAY || + dst->target == PIPE_TEXTURE_CUBE_ARRAY) layers = dst->array_size; else layers = u_minify(dst->depth0, level); -- 2.30.2