17c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca/**************************************************************************
27c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca *
37c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca * Copyright 2010 VMware, Inc.
47c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca * All Rights Reserved.
57c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca *
67c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca * Permission is hereby granted, free of charge, to any person obtaining a
77c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca * copy of this software and associated documentation files (the
87c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca * "Software"), to deal in the Software without restriction, including
97c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca * without limitation the rights to use, copy, modify, merge, publish,
107c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca * distribute, sub license, and/or sell copies of the Software, and to
117c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca * permit persons to whom the Software is furnished to do so, subject to
127c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca * the following conditions:
137c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca *
147c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
157c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
167c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
177c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca * THE COPYRIGHT HOLDERS, AUTHORS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM,
187c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
197c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca * OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE
207c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca * USE OR OTHER DEALINGS IN THE SOFTWARE.
217c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca *
227c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca * The above copyright notice and this permission notice (including the
237c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca * next paragraph) shall be included in all copies or substantial portions
247c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca * of the Software.
257c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca *
267c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca **************************************************************************/
277c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
287c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
297c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca#include "util/u_memory.h"
307c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca#include "util/u_math.h"
317c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca#include "tgsi/tgsi_parse.h"
327c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca#include "tgsi/tgsi_util.h"
337c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca#include "tgsi/tgsi_dump.h"
3485b5dac705fcf3fafb734696e1f863cfc21e2d6eBrian Paul#include "tgsi/tgsi_strings.h"
357c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca#include "lp_bld_debug.h"
367c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca#include "lp_bld_tgsi.h"
377c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
387c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
397c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca/**
407c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca * Analysis context.
417c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca *
427c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca * This is where we keep store the value of each channel of the IMM/TEMP/OUT
437c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca * register values, as we walk the shader.
447c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca */
457c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonsecastruct analysis_context
467c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca{
477c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   struct lp_tgsi_info *info;
487c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
497c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   unsigned num_imms;
507045f222cdd3a50f03e66ae2c184af17d9c32364Brian Paul   float imm[128][4];
517c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
527c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   struct lp_tgsi_channel_info temp[32][4];
537c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca};
547c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
557c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
567c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca/**
577c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca * Describe the specified channel of the src register.
587c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca */
597c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonsecastatic void
607c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonsecaanalyse_src(struct analysis_context *ctx,
617c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca            struct lp_tgsi_channel_info *chan_info,
627c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca            const struct tgsi_src_register *src,
637c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca            unsigned chan)
647c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca{
657c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   chan_info->file = TGSI_FILE_NULL;
667c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   if (!src->Indirect && !src->Absolute && !src->Negate) {
677c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      unsigned swizzle = tgsi_util_get_src_register_swizzle(src, chan);
687c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      if (src->File == TGSI_FILE_TEMPORARY) {
697c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         if (src->Index < Elements(ctx->temp)) {
707c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca            *chan_info = ctx->temp[src->Index][swizzle];
717c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         }
727c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      } else {
737c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         chan_info->file = src->File;
747c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         if (src->File == TGSI_FILE_IMMEDIATE) {
757c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca            assert(src->Index < Elements(ctx->imm));
767c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca            if (src->Index < Elements(ctx->imm)) {
776fbd4faf971a0091815211c4d1385c9a4fb0adc6José Fonseca               chan_info->u.value = ctx->imm[src->Index][swizzle];
787c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca            }
797c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         } else {
806fbd4faf971a0091815211c4d1385c9a4fb0adc6José Fonseca            chan_info->u.index = src->Index;
817c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca            chan_info->swizzle = swizzle;
827c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         }
837c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      }
847c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   }
857c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca}
867c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
877c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
887c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca/**
897c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca * Whether this register channel refers to a specific immediate value.
907c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca */
917c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonsecastatic boolean
927c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonsecais_immediate(const struct lp_tgsi_channel_info *chan_info, float value)
937c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca{
947c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   return chan_info->file == TGSI_FILE_IMMEDIATE &&
956fbd4faf971a0091815211c4d1385c9a4fb0adc6José Fonseca          chan_info->u.value == value;
967c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca}
977c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
987c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
997c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonsecastatic void
1007c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonsecaanalyse_tex(struct analysis_context *ctx,
1017c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca            const struct tgsi_full_instruction *inst,
1027c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca            enum lp_build_tex_modifier modifier)
1037c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca{
1047c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   struct lp_tgsi_info *info = ctx->info;
1057c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   unsigned chan;
1067c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
1077c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   if (info->num_texs < Elements(info->tex)) {
1087c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      struct lp_tgsi_texture_info *tex_info = &info->tex[info->num_texs];
1095f2deba9f3f3f9230a9fdd2848e20c1e23e98b8fBrian Paul      boolean indirect = FALSE;
1107c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      unsigned readmask = 0;
1117c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
1127c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      tex_info->target = inst->Texture.Texture;
1137c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      switch (inst->Texture.Texture) {
1147c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      case TGSI_TEXTURE_1D:
1157c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         readmask = TGSI_WRITEMASK_X;
1167c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         break;
117d8452a0be810d7176b0cbfe6632fc0f8016b5733Marek Olšák      case TGSI_TEXTURE_1D_ARRAY:
1187c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      case TGSI_TEXTURE_2D:
1197c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      case TGSI_TEXTURE_RECT:
1207c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         readmask = TGSI_WRITEMASK_XY;
1217c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         break;
1227c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      case TGSI_TEXTURE_SHADOW1D:
123d8452a0be810d7176b0cbfe6632fc0f8016b5733Marek Olšák      case TGSI_TEXTURE_SHADOW1D_ARRAY:
1247c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      case TGSI_TEXTURE_SHADOW2D:
1257c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      case TGSI_TEXTURE_SHADOWRECT:
126d8452a0be810d7176b0cbfe6632fc0f8016b5733Marek Olšák      case TGSI_TEXTURE_2D_ARRAY:
1277c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      case TGSI_TEXTURE_3D:
1287c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      case TGSI_TEXTURE_CUBE:
1297c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         readmask = TGSI_WRITEMASK_XYZ;
1307c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         break;
131d8452a0be810d7176b0cbfe6632fc0f8016b5733Marek Olšák      case TGSI_TEXTURE_SHADOW2D_ARRAY:
132d8452a0be810d7176b0cbfe6632fc0f8016b5733Marek Olšák         readmask = TGSI_WRITEMASK_XYZW;
133d8452a0be810d7176b0cbfe6632fc0f8016b5733Marek Olšák         break;
1347c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      default:
1357c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         assert(0);
1367c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         return;
1377c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      }
1387c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
1397c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      if (modifier == LP_BLD_TEX_MODIFIER_EXPLICIT_DERIV) {
1407c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         /* We don't track explicit derivatives, although we could */
1417c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         indirect = TRUE;
1427c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         tex_info->unit = inst->Src[3].Register.Index;
1437c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      }  else {
1447c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         if (modifier == LP_BLD_TEX_MODIFIER_PROJECTED ||
1457c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca             modifier == LP_BLD_TEX_MODIFIER_LOD_BIAS ||
1467c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca             modifier == LP_BLD_TEX_MODIFIER_EXPLICIT_LOD) {
1477c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca            readmask |= TGSI_WRITEMASK_W;
1487c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         }
1497c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         tex_info->unit = inst->Src[1].Register.Index;
1507c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      }
1517c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
1527c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      for (chan = 0; chan < 4; ++chan) {
1537c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         struct lp_tgsi_channel_info *chan_info = &tex_info->coord[chan];
1547c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         if (readmask & (1 << chan)) {
1557c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca            analyse_src(ctx, chan_info, &inst->Src[0].Register, chan);
1567c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca            if (chan_info->file != TGSI_FILE_INPUT) {
1577c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca               indirect = TRUE;
1587c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca            }
1597c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         } else {
1607c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca            memset(chan_info, 0, sizeof *chan_info);
1617c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         }
1627c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      }
1637c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
1647c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      if (indirect) {
1657c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         info->indirect_textures = TRUE;
1667c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      }
1677c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
1687c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      ++info->num_texs;
1697c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   } else {
1707c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      info->indirect_textures = TRUE;
1717c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   }
1727c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca}
1737c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
1747c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
1757c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca/**
1767c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca * Process an instruction, and update the register values accordingly.
1777c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca */
1787c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonsecastatic void
1797c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonsecaanalyse_instruction(struct analysis_context *ctx,
1807c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca                    struct tgsi_full_instruction *inst)
1817c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca{
1827c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   struct lp_tgsi_info *info = ctx->info;
1837c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   struct lp_tgsi_channel_info (*regs)[4];
1847c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   unsigned max_regs;
1857c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   unsigned i;
1867c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   unsigned index;
1877c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   unsigned chan;
1887c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
1897c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   for (i = 0; i < inst->Instruction.NumDstRegs; ++i) {
1907c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      const struct tgsi_dst_register *dst = &inst->Dst[i].Register;
1917c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
1927c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      /*
1937c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca       * Get the lp_tgsi_channel_info array corresponding to the destination
1947c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca       * register file.
1957c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca       */
1967c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
1977c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      if (dst->File == TGSI_FILE_TEMPORARY) {
1987c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         regs = ctx->temp;
1997c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         max_regs = Elements(ctx->temp);
2007c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      } else if (dst->File == TGSI_FILE_OUTPUT) {
2017c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         regs = info->output;
2027c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         max_regs = Elements(info->output);
2037c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      } else if (dst->File == TGSI_FILE_ADDRESS ||
2047c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca                 dst->File == TGSI_FILE_PREDICATE) {
2057c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         continue;
2067c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      } else {
2077c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         assert(0);
2087c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         continue;
2097c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      }
2107c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
2117c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      /*
2127c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca       * Detect direct TEX instructions
2137c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca       */
2147c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
2157c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      switch (inst->Instruction.Opcode) {
2167c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      case TGSI_OPCODE_TEX:
2177c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         analyse_tex(ctx, inst, LP_BLD_TEX_MODIFIER_NONE);
2187c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         break;
2197c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      case TGSI_OPCODE_TXD:
2207c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         analyse_tex(ctx, inst, LP_BLD_TEX_MODIFIER_EXPLICIT_DERIV);
2217c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         break;
2227c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      case TGSI_OPCODE_TXB:
2237c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         analyse_tex(ctx, inst, LP_BLD_TEX_MODIFIER_LOD_BIAS);
2247c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         break;
2257c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      case TGSI_OPCODE_TXL:
2267c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         analyse_tex(ctx, inst, LP_BLD_TEX_MODIFIER_EXPLICIT_LOD);
2277c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         break;
2287c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      case TGSI_OPCODE_TXP:
2297c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         analyse_tex(ctx, inst, LP_BLD_TEX_MODIFIER_PROJECTED);
2307c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         break;
2317c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      default:
2327c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         break;
2337c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      }
2347c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
2357c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      /*
2367c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca       * Keep track of assignments and writes
2377c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca       */
2387c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
2397c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      if (dst->Indirect) {
2407c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         /*
2417c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca          * It could be any register index so clear all register indices.
2427c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca          */
2437c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
2447c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         for (chan = 0; chan < 4; ++chan) {
2457c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca            if (dst->WriteMask & (1 << chan)) {
2467c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca               for (index = 0; index < max_regs; ++index) {
2477c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca                  regs[index][chan].file = TGSI_FILE_NULL;
2487c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca               }
2497c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca            }
2507c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         }
2517c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      } else if (dst->Index < max_regs) {
2527c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         /*
2537c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca          * Update this destination register value.
2547c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca          */
2557c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
2567c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         struct lp_tgsi_channel_info res[4];
2577c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
2587c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         memset(res, 0, sizeof res);
2597c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
2607c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         if (!inst->Instruction.Predicate &&
2617c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca             !inst->Instruction.Saturate) {
2627c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca            for (chan = 0; chan < 4; ++chan) {
2637c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca               if (dst->WriteMask & (1 << chan)) {
2647c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca                  if (inst->Instruction.Opcode == TGSI_OPCODE_MOV) {
2657c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca                     analyse_src(ctx, &res[chan],
2667c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca                                 &inst->Src[0].Register, chan);
2677c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca                  } else if (inst->Instruction.Opcode == TGSI_OPCODE_MUL) {
2687c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca                     /*
2697c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca                      * Propagate values across 1.0 and 0.0 multiplications.
2707c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca                      */
2717c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
2727c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca                     struct lp_tgsi_channel_info src0;
2737c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca                     struct lp_tgsi_channel_info src1;
2747c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
2757c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca                     analyse_src(ctx, &src0, &inst->Src[0].Register, chan);
2767c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca                     analyse_src(ctx, &src1, &inst->Src[1].Register, chan);
2777c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
2787c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca                     if (is_immediate(&src0, 0.0f)) {
2797c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca                        res[chan] = src0;
2807c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca                     } else if (is_immediate(&src1, 0.0f)) {
2817c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca                        res[chan] = src1;
2827c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca                     } else if (is_immediate(&src0, 1.0f)) {
2837c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca                        res[chan] = src1;
2847c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca                     } else if (is_immediate(&src1, 1.0f)) {
2857c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca                        res[chan] = src0;
2867c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca                     }
2877c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca                  }
2887c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca               }
2897c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca            }
2907c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         }
2917c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
2927c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         for (chan = 0; chan < 4; ++chan) {
2937c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca            if (dst->WriteMask & (1 << chan)) {
2947c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca               regs[dst->Index][chan] = res[chan];
2957c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca            }
2967c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         }
2977c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      }
2987c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   }
2997c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
3007c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   /*
3017c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca    * Clear all temporaries information in presence of a control flow opcode.
3027c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca    */
3037c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
3047c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   switch (inst->Instruction.Opcode) {
3057c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   case TGSI_OPCODE_IF:
3067c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   case TGSI_OPCODE_IFC:
3077c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   case TGSI_OPCODE_ELSE:
3087c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   case TGSI_OPCODE_ENDIF:
3097c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   case TGSI_OPCODE_BGNLOOP:
3107c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   case TGSI_OPCODE_BRK:
3117c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   case TGSI_OPCODE_BREAKC:
3127c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   case TGSI_OPCODE_CONT:
3137c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   case TGSI_OPCODE_ENDLOOP:
3147c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   case TGSI_OPCODE_CALLNZ:
3157c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   case TGSI_OPCODE_CAL:
3167c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   case TGSI_OPCODE_BGNSUB:
3177c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   case TGSI_OPCODE_ENDSUB:
3187c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   case TGSI_OPCODE_SWITCH:
3197c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   case TGSI_OPCODE_CASE:
3207c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   case TGSI_OPCODE_DEFAULT:
3217c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   case TGSI_OPCODE_ENDSWITCH:
3227c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   case TGSI_OPCODE_RET:
3237c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   case TGSI_OPCODE_END:
3247c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      /* XXX: Are there more cases? */
3257c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      memset(&ctx->temp, 0, sizeof ctx->temp);
3267c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      memset(&info->output, 0, sizeof info->output);
3277c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   default:
3287c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      break;
3297c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   }
3307c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca}
3317c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
3327c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
3337c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonsecastatic INLINE void
3347c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonsecadump_info(const struct tgsi_token *tokens,
3357c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca          struct lp_tgsi_info *info)
3367c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca{
3377c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   unsigned index;
3387c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   unsigned chan;
3397c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
3407c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   tgsi_dump(tokens, 0);
3417c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
3427c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   for (index = 0; index < info->num_texs; ++index) {
3437c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      const struct lp_tgsi_texture_info *tex_info = &info->tex[index];
3447c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      debug_printf("TEX[%u] =", index);
3457c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      for (chan = 0; chan < 4; ++chan) {
3467c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         const struct lp_tgsi_channel_info *chan_info =
3477c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca               &tex_info->coord[chan];
3487c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         if (chan_info->file != TGSI_FILE_NULL) {
3497c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca            debug_printf(" %s[%u].%c",
3507c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca                         tgsi_file_names[chan_info->file],
3516fbd4faf971a0091815211c4d1385c9a4fb0adc6José Fonseca                         chan_info->u.index,
3527c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca                         "xyzw01"[chan_info->swizzle]);
3537c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         } else {
3547c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca            debug_printf(" _");
3557c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         }
3567c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      }
3577c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      debug_printf(", SAMP[%u], %s\n",
3587c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca                   tex_info->unit,
3597c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca                   tgsi_texture_names[tex_info->target]);
3607c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   }
3617c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
3627c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   for (index = 0; index < PIPE_MAX_SHADER_OUTPUTS; ++index) {
3637c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      for (chan = 0; chan < 4; ++chan) {
3647c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         const struct lp_tgsi_channel_info *chan_info =
3657c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca               &info->output[index][chan];
3667c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         if (chan_info->file != TGSI_FILE_NULL) {
3677c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca            debug_printf("OUT[%u].%c = ", index, "xyzw"[chan]);
3687c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca            if (chan_info->file == TGSI_FILE_IMMEDIATE) {
3696fbd4faf971a0091815211c4d1385c9a4fb0adc6José Fonseca               debug_printf("%f", chan_info->u.value);
3707c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca            } else {
3717c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca               const char *file_name;
3727c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca               switch (chan_info->file) {
3737c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca               case TGSI_FILE_CONSTANT:
3747c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca                  file_name = "CONST";
3757c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca                  break;
3767c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca               case TGSI_FILE_INPUT:
3777c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca                  file_name = "IN";
3787c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca                  break;
3797c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca               default:
3807c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca                  file_name = "???";
3817c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca                  break;
3827c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca               }
3837c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca               debug_printf("%s[%u].%c",
3847c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca                            file_name,
3856fbd4faf971a0091815211c4d1385c9a4fb0adc6José Fonseca                            chan_info->u.index,
3867c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca                            "xyzw01"[chan_info->swizzle]);
3877c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca            }
3887c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca            debug_printf("\n");
3897c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         }
3907c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      }
3917c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   }
3927c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca}
3937c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
3947c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
3957c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca/**
3967c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca * Detect any direct relationship between the output color
3977c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca */
3987c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonsecavoid
3997c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonsecalp_build_tgsi_info(const struct tgsi_token *tokens,
4007c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca                   struct lp_tgsi_info *info)
4017c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca{
4027c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   struct tgsi_parse_context parse;
4037c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   struct analysis_context ctx;
4047c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   unsigned index;
4057c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   unsigned chan;
4067c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
4077c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   memset(info, 0, sizeof *info);
4087c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
4097c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   tgsi_scan_shader(tokens, &info->base);
4107c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
4117c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   memset(&ctx, 0, sizeof ctx);
4127c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   ctx.info = info;
4137c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
4147c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   tgsi_parse_init(&parse, tokens);
4157c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
4167c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   while (!tgsi_parse_end_of_tokens(&parse)) {
4177c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      tgsi_parse_token(&parse);
4187c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
4197c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      switch (parse.FullToken.Token.Type) {
4207c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      case TGSI_TOKEN_TYPE_DECLARATION:
4217c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         break;
4227c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
4237c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      case TGSI_TOKEN_TYPE_INSTRUCTION:
4247c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         {
4257c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca            struct tgsi_full_instruction *inst =
4267c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca                  &parse.FullToken.FullInstruction;
4277c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
4287c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca            if (inst->Instruction.Opcode == TGSI_OPCODE_END ||
4297c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca                inst->Instruction.Opcode == TGSI_OPCODE_BGNSUB) {
4307c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca               /* We reached the end of main function body. */
4317c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca               goto finished;
4327c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca            }
4337c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
4347c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca            analyse_instruction(&ctx, inst);
4357c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         }
4367c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         break;
4377c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
4387c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      case TGSI_TOKEN_TYPE_IMMEDIATE:
4397c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         {
4407c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca            const unsigned size =
4417c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca                  parse.FullToken.FullImmediate.Immediate.NrTokens - 1;
4427c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca            assert(size <= 4);
4437c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca            if (ctx.num_imms < Elements(ctx.imm)) {
4447c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca               for (chan = 0; chan < size; ++chan) {
4459bc58d941ac32d10c6b4c601e0c4c6e00876d738James Benton                  float value = parse.FullToken.FullImmediate.u[chan].Float;
4469bc58d941ac32d10c6b4c601e0c4c6e00876d738James Benton                  ctx.imm[ctx.num_imms][chan] = value;
4479bc58d941ac32d10c6b4c601e0c4c6e00876d738James Benton
4489bc58d941ac32d10c6b4c601e0c4c6e00876d738James Benton                  if (value < 0.0f || value > 1.0f) {
4499bc58d941ac32d10c6b4c601e0c4c6e00876d738James Benton                     info->unclamped_immediates = TRUE;
4509bc58d941ac32d10c6b4c601e0c4c6e00876d738James Benton                  }
4517c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca               }
4527c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca               ++ctx.num_imms;
4537c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca            }
4547c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         }
4557c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         break;
4567c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
4577c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      case TGSI_TOKEN_TYPE_PROPERTY:
4587c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         break;
4597c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
4607c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      default:
4617c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         assert(0);
4627c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      }
4637c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   }
4647c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonsecafinished:
4657c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
4667c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   tgsi_parse_free(&parse);
4677c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
4687c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
4697c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   /*
4707c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca    * Link the output color values.
4717c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca    */
4727c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
4737c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   for (index = 0; index < PIPE_MAX_COLOR_BUFS; ++index) {
4747c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      const struct lp_tgsi_channel_info null_output[4];
4757c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      info->cbuf[index] = null_output;
4767c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   }
4777c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
4787c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   for (index = 0; index < info->base.num_outputs; ++index) {
4797c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      unsigned semantic_name = info->base.output_semantic_name[index];
4807c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      unsigned semantic_index = info->base.output_semantic_index[index];
4817c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      if (semantic_name == TGSI_SEMANTIC_COLOR &&
4827c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca          semantic_index < PIPE_MAX_COLOR_BUFS) {
4837c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca         info->cbuf[semantic_index] = info->output[index];
4847c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      }
4857c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   }
4867c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca
4877c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   if (gallivm_debug & GALLIVM_DEBUG_TGSI) {
4887c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca      dump_info(tokens, info);
4897c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca   }
4907c1b5772a81c4f701ae9a6208c9e34792c05d4abJosé Fonseca}
491