1.1 --- /dev/null Thu Jan 01 00:00:00 1970 +0000 1.2 +++ b/gfx/angle/src/compiler/VariableInfo.cpp Wed Dec 31 06:09:35 2014 +0100 1.3 @@ -0,0 +1,245 @@ 1.4 +// 1.5 +// Copyright (c) 2002-2010 The ANGLE Project Authors. All rights reserved. 1.6 +// Use of this source code is governed by a BSD-style license that can be 1.7 +// found in the LICENSE file. 1.8 +// 1.9 + 1.10 +#include "compiler/VariableInfo.h" 1.11 + 1.12 +static TString arrayBrackets(int index) 1.13 +{ 1.14 + TStringStream stream; 1.15 + stream << "[" << index << "]"; 1.16 + return stream.str(); 1.17 +} 1.18 + 1.19 +// Returns the data type for an attribute or uniform. 1.20 +static ShDataType getVariableDataType(const TType& type) 1.21 +{ 1.22 + switch (type.getBasicType()) { 1.23 + case EbtFloat: 1.24 + if (type.isMatrix()) { 1.25 + switch (type.getNominalSize()) { 1.26 + case 2: return SH_FLOAT_MAT2; 1.27 + case 3: return SH_FLOAT_MAT3; 1.28 + case 4: return SH_FLOAT_MAT4; 1.29 + default: UNREACHABLE(); 1.30 + } 1.31 + } else if (type.isVector()) { 1.32 + switch (type.getNominalSize()) { 1.33 + case 2: return SH_FLOAT_VEC2; 1.34 + case 3: return SH_FLOAT_VEC3; 1.35 + case 4: return SH_FLOAT_VEC4; 1.36 + default: UNREACHABLE(); 1.37 + } 1.38 + } else { 1.39 + return SH_FLOAT; 1.40 + } 1.41 + case EbtInt: 1.42 + if (type.isMatrix()) { 1.43 + UNREACHABLE(); 1.44 + } else if (type.isVector()) { 1.45 + switch (type.getNominalSize()) { 1.46 + case 2: return SH_INT_VEC2; 1.47 + case 3: return SH_INT_VEC3; 1.48 + case 4: return SH_INT_VEC4; 1.49 + default: UNREACHABLE(); 1.50 + } 1.51 + } else { 1.52 + return SH_INT; 1.53 + } 1.54 + case EbtBool: 1.55 + if (type.isMatrix()) { 1.56 + UNREACHABLE(); 1.57 + } else if (type.isVector()) { 1.58 + switch (type.getNominalSize()) { 1.59 + case 2: return SH_BOOL_VEC2; 1.60 + case 3: return SH_BOOL_VEC3; 1.61 + case 4: return SH_BOOL_VEC4; 1.62 + default: UNREACHABLE(); 1.63 + } 1.64 + } else { 1.65 + return SH_BOOL; 1.66 + } 1.67 + case EbtSampler2D: return SH_SAMPLER_2D; 1.68 + case EbtSamplerCube: return SH_SAMPLER_CUBE; 1.69 + case EbtSamplerExternalOES: return SH_SAMPLER_EXTERNAL_OES; 1.70 + case EbtSampler2DRect: return SH_SAMPLER_2D_RECT_ARB; 1.71 + default: UNREACHABLE(); 1.72 + } 1.73 + return SH_NONE; 1.74 +} 1.75 + 1.76 +static void getBuiltInVariableInfo(const TType& type, 1.77 + const TString& name, 1.78 + const TString& mappedName, 1.79 + TVariableInfoList& infoList); 1.80 +static void getUserDefinedVariableInfo(const TType& type, 1.81 + const TString& name, 1.82 + const TString& mappedName, 1.83 + TVariableInfoList& infoList, 1.84 + ShHashFunction64 hashFunction); 1.85 + 1.86 +// Returns info for an attribute or uniform. 1.87 +static void getVariableInfo(const TType& type, 1.88 + const TString& name, 1.89 + const TString& mappedName, 1.90 + TVariableInfoList& infoList, 1.91 + ShHashFunction64 hashFunction) 1.92 +{ 1.93 + if (type.getBasicType() == EbtStruct) { 1.94 + if (type.isArray()) { 1.95 + for (int i = 0; i < type.getArraySize(); ++i) { 1.96 + TString lname = name + arrayBrackets(i); 1.97 + TString lmappedName = mappedName + arrayBrackets(i); 1.98 + getUserDefinedVariableInfo(type, lname, lmappedName, infoList, hashFunction); 1.99 + } 1.100 + } else { 1.101 + getUserDefinedVariableInfo(type, name, mappedName, infoList, hashFunction); 1.102 + } 1.103 + } else { 1.104 + getBuiltInVariableInfo(type, name, mappedName, infoList); 1.105 + } 1.106 +} 1.107 + 1.108 +void getBuiltInVariableInfo(const TType& type, 1.109 + const TString& name, 1.110 + const TString& mappedName, 1.111 + TVariableInfoList& infoList) 1.112 +{ 1.113 + ASSERT(type.getBasicType() != EbtStruct); 1.114 + 1.115 + TVariableInfo varInfo; 1.116 + if (type.isArray()) { 1.117 + varInfo.name = (name + "[0]").c_str(); 1.118 + varInfo.mappedName = (mappedName + "[0]").c_str(); 1.119 + varInfo.size = type.getArraySize(); 1.120 + } else { 1.121 + varInfo.name = name.c_str(); 1.122 + varInfo.mappedName = mappedName.c_str(); 1.123 + varInfo.size = 1; 1.124 + } 1.125 + varInfo.type = getVariableDataType(type); 1.126 + infoList.push_back(varInfo); 1.127 +} 1.128 + 1.129 +void getUserDefinedVariableInfo(const TType& type, 1.130 + const TString& name, 1.131 + const TString& mappedName, 1.132 + TVariableInfoList& infoList, 1.133 + ShHashFunction64 hashFunction) 1.134 +{ 1.135 + ASSERT(type.getBasicType() == EbtStruct); 1.136 + 1.137 + const TFieldList& fields = type.getStruct()->fields(); 1.138 + for (size_t i = 0; i < fields.size(); ++i) { 1.139 + const TType& fieldType = *(fields[i]->type()); 1.140 + const TString& fieldName = fields[i]->name(); 1.141 + getVariableInfo(fieldType, 1.142 + name + "." + fieldName, 1.143 + mappedName + "." + TIntermTraverser::hash(fieldName, hashFunction), 1.144 + infoList, 1.145 + hashFunction); 1.146 + } 1.147 +} 1.148 + 1.149 +TVariableInfo::TVariableInfo() 1.150 +{ 1.151 +} 1.152 + 1.153 +TVariableInfo::TVariableInfo(ShDataType type, int size) 1.154 + : type(type), 1.155 + size(size) 1.156 +{ 1.157 +} 1.158 + 1.159 +CollectAttribsUniforms::CollectAttribsUniforms(TVariableInfoList& attribs, 1.160 + TVariableInfoList& uniforms, 1.161 + ShHashFunction64 hashFunction) 1.162 + : mAttribs(attribs), 1.163 + mUniforms(uniforms), 1.164 + mHashFunction(hashFunction) 1.165 +{ 1.166 +} 1.167 + 1.168 +// We are only interested in attribute and uniform variable declaration. 1.169 +void CollectAttribsUniforms::visitSymbol(TIntermSymbol*) 1.170 +{ 1.171 +} 1.172 + 1.173 +void CollectAttribsUniforms::visitConstantUnion(TIntermConstantUnion*) 1.174 +{ 1.175 +} 1.176 + 1.177 +bool CollectAttribsUniforms::visitBinary(Visit, TIntermBinary*) 1.178 +{ 1.179 + return false; 1.180 +} 1.181 + 1.182 +bool CollectAttribsUniforms::visitUnary(Visit, TIntermUnary*) 1.183 +{ 1.184 + return false; 1.185 +} 1.186 + 1.187 +bool CollectAttribsUniforms::visitSelection(Visit, TIntermSelection*) 1.188 +{ 1.189 + return false; 1.190 +} 1.191 + 1.192 +bool CollectAttribsUniforms::visitAggregate(Visit, TIntermAggregate* node) 1.193 +{ 1.194 + bool visitChildren = false; 1.195 + 1.196 + switch (node->getOp()) 1.197 + { 1.198 + case EOpSequence: 1.199 + // We need to visit sequence children to get to variable declarations. 1.200 + visitChildren = true; 1.201 + break; 1.202 + case EOpDeclaration: { 1.203 + const TIntermSequence& sequence = node->getSequence(); 1.204 + TQualifier qualifier = sequence.front()->getAsTyped()->getQualifier(); 1.205 + if (qualifier == EvqAttribute || qualifier == EvqUniform) 1.206 + { 1.207 + TVariableInfoList& infoList = qualifier == EvqAttribute ? 1.208 + mAttribs : mUniforms; 1.209 + for (TIntermSequence::const_iterator i = sequence.begin(); 1.210 + i != sequence.end(); ++i) 1.211 + { 1.212 + const TIntermSymbol* variable = (*i)->getAsSymbolNode(); 1.213 + // The only case in which the sequence will not contain a 1.214 + // TIntermSymbol node is initialization. It will contain a 1.215 + // TInterBinary node in that case. Since attributes and unifroms 1.216 + // cannot be initialized in a shader, we must have only 1.217 + // TIntermSymbol nodes in the sequence. 1.218 + ASSERT(variable != NULL); 1.219 + TString processedSymbol; 1.220 + if (mHashFunction == NULL) 1.221 + processedSymbol = variable->getSymbol(); 1.222 + else 1.223 + processedSymbol = TIntermTraverser::hash(variable->getOriginalSymbol(), mHashFunction); 1.224 + getVariableInfo(variable->getType(), 1.225 + variable->getOriginalSymbol(), 1.226 + processedSymbol, 1.227 + infoList, 1.228 + mHashFunction); 1.229 + } 1.230 + } 1.231 + break; 1.232 + } 1.233 + default: break; 1.234 + } 1.235 + 1.236 + return visitChildren; 1.237 +} 1.238 + 1.239 +bool CollectAttribsUniforms::visitLoop(Visit, TIntermLoop*) 1.240 +{ 1.241 + return false; 1.242 +} 1.243 + 1.244 +bool CollectAttribsUniforms::visitBranch(Visit, TIntermBranch*) 1.245 +{ 1.246 + return false; 1.247 +} 1.248 +