blob: 75cdbf93e9fde65d92fcdaea21ad1d64219466e5 [file] [log] [blame]
alokp@chromium.org07620a52010-09-23 17:53:56 +00001//
2// Copyright (c) 2002-2010 The ANGLE Project Authors. All rights reserved.
3// Use of this source code is governed by a BSD-style license that can be
4// found in the LICENSE file.
5//
6
7#include "compiler/VariableInfo.h"
8
alokp@chromium.orgee76f6a2010-09-27 19:28:55 +00009static TString arrayBrackets(int index)
10{
11 TStringStream stream;
12 stream << "[" << index << "]";
13 return stream.str();
14}
15
16// Returns the data type for an attribute or uniform.
17static EShDataType getVariableDataType(const TType& type)
18{
19 switch (type.getBasicType()) {
20 case EbtFloat:
21 if (type.isMatrix()) {
22 switch (type.getNominalSize()) {
23 case 2: return SH_FLOAT_MAT2;
24 case 3: return SH_FLOAT_MAT3;
25 case 4: return SH_FLOAT_MAT4;
26 default: UNREACHABLE();
27 }
28 } else if (type.isVector()) {
29 switch (type.getNominalSize()) {
30 case 2: return SH_FLOAT_VEC2;
31 case 3: return SH_FLOAT_VEC3;
32 case 4: return SH_FLOAT_VEC4;
33 default: UNREACHABLE();
34 }
35 } else {
36 return SH_FLOAT;
37 }
38 case EbtInt:
39 if (type.isMatrix()) {
40 UNREACHABLE();
41 } else if (type.isVector()) {
42 switch (type.getNominalSize()) {
43 case 2: return SH_INT_VEC2;
44 case 3: return SH_INT_VEC3;
45 case 4: return SH_INT_VEC4;
46 default: UNREACHABLE();
47 }
48 } else {
49 return SH_INT;
50 }
51 case EbtBool:
52 if (type.isMatrix()) {
53 UNREACHABLE();
54 } else if (type.isVector()) {
55 switch (type.getNominalSize()) {
56 case 2: return SH_BOOL_VEC2;
57 case 3: return SH_BOOL_VEC3;
58 case 4: return SH_BOOL_VEC4;
59 default: UNREACHABLE();
60 }
61 } else {
62 return SH_BOOL;
63 }
64 case EbtSampler2D: return SH_SAMPLER_2D;
65 case EbtSamplerCube: return SH_SAMPLER_CUBE;
66 default: UNREACHABLE();
67 }
68 return SH_NONE;
69}
70
71static void getBuiltInVariableInfo(const TType& type,
72 const TString& name,
73 TVariableInfoList& infoList);
74static void getUserDefinedVariableInfo(const TType& type,
75 const TString& name,
76 TVariableInfoList& infoList);
77
78// Returns info for an attribute or uniform.
79static void getVariableInfo(const TType& type,
80 const TString& name,
81 TVariableInfoList& infoList)
82{
83 if (type.getBasicType() == EbtStruct) {
84 if (type.isArray()) {
85 for (int i = 0; i < type.getArraySize(); ++i) {
86 TString lname = name + arrayBrackets(i);
87 getUserDefinedVariableInfo(type, lname, infoList);
88 }
89 } else {
90 getUserDefinedVariableInfo(type, name, infoList);
91 }
92 } else {
93 getBuiltInVariableInfo(type, name, infoList);
94 }
95}
96
97void getBuiltInVariableInfo(const TType& type,
98 const TString& name,
99 TVariableInfoList& infoList)
100{
101 ASSERT(type.getBasicType() != EbtStruct);
102
103 TVariableInfo varInfo;
104 if (type.isArray()) {
105 varInfo.name = (name + "[0]").c_str();
106 varInfo.size = type.getArraySize();
107 } else {
108 varInfo.name = name.c_str();
109 varInfo.size = 1;
110 }
111 varInfo.type = getVariableDataType(type);
112 infoList.push_back(varInfo);
113}
114
115void getUserDefinedVariableInfo(const TType& type,
116 const TString& name,
117 TVariableInfoList& infoList)
118{
119 ASSERT(type.getBasicType() == EbtStruct);
120
121 TString lname = name + ".";
122 const TTypeList* structure = type.getStruct();
123 for (size_t i = 0; i < structure->size(); ++i) {
124 const TType* fieldType = (*structure)[i].type;
125 getVariableInfo(*fieldType,
126 lname + fieldType->getFieldName(),
127 infoList);
128 }
129}
130
alokp@chromium.org07620a52010-09-23 17:53:56 +0000131CollectAttribsUniforms::CollectAttribsUniforms(TVariableInfoList& attribs,
132 TVariableInfoList& uniforms)
133 : mAttribs(attribs),
134 mUniforms(uniforms)
135{
136}
137
alokp@chromium.orgee76f6a2010-09-27 19:28:55 +0000138// We are only interested in attribute and uniform variable declaration.
alokp@chromium.org07620a52010-09-23 17:53:56 +0000139void CollectAttribsUniforms::visitSymbol(TIntermSymbol*)
140{
141}
142
143void CollectAttribsUniforms::visitConstantUnion(TIntermConstantUnion*)
144{
145}
146
alokp@chromium.orgee76f6a2010-09-27 19:28:55 +0000147bool CollectAttribsUniforms::visitBinary(Visit, TIntermBinary*)
alokp@chromium.org07620a52010-09-23 17:53:56 +0000148{
149 return false;
150}
151
alokp@chromium.orgee76f6a2010-09-27 19:28:55 +0000152bool CollectAttribsUniforms::visitUnary(Visit, TIntermUnary*)
alokp@chromium.org07620a52010-09-23 17:53:56 +0000153{
154 return false;
155}
156
alokp@chromium.orgee76f6a2010-09-27 19:28:55 +0000157bool CollectAttribsUniforms::visitSelection(Visit, TIntermSelection*)
alokp@chromium.org07620a52010-09-23 17:53:56 +0000158{
159 return false;
160}
161
alokp@chromium.orgee76f6a2010-09-27 19:28:55 +0000162bool CollectAttribsUniforms::visitAggregate(Visit, TIntermAggregate* node)
163{
164 bool visitChildren = false;
165
166 switch (node->getOp())
167 {
168 case EOpSequence:
169 // We need to visit sequence children to get to variable declarations.
170 visitChildren = true;
171 break;
172 case EOpDeclaration: {
173 const TIntermSequence& sequence = node->getSequence();
alokp@chromium.org10e6e9e2010-09-27 21:03:45 +0000174 TQualifier qualifier = sequence.front()->getAsTyped()->getQualifier();
alokp@chromium.orgee76f6a2010-09-27 19:28:55 +0000175 if (qualifier == EvqAttribute || qualifier == EvqUniform)
176 {
177 TVariableInfoList& infoList = qualifier == EvqAttribute ?
178 mAttribs : mUniforms;
179 for (TIntermSequence::const_iterator i = sequence.begin();
180 i != sequence.end(); ++i)
181 {
alokp@chromium.org10e6e9e2010-09-27 21:03:45 +0000182 const TIntermSymbol* variable = (*i)->getAsSymbolNode();
183 // The only case in which the sequence will not contain a
184 // TIntermSymbol node is initialization. It will contain a
185 // TInterBinary node in that case. Since attributes and unifroms
186 // cannot be initialized in a shader, we must have only
187 // TIntermSymbol nodes in the sequence.
188 ASSERT(variable != NULL);
alokp@chromium.orgee76f6a2010-09-27 19:28:55 +0000189 getVariableInfo(variable->getType(), variable->getSymbol(),
190 infoList);
191 }
192 }
193 break;
194 }
195 default: break;
196 }
197
198 return visitChildren;
199}
200
201bool CollectAttribsUniforms::visitLoop(Visit, TIntermLoop*)
alokp@chromium.org07620a52010-09-23 17:53:56 +0000202{
203 return false;
204}
205
alokp@chromium.orgee76f6a2010-09-27 19:28:55 +0000206bool CollectAttribsUniforms::visitBranch(Visit, TIntermBranch*)
alokp@chromium.org07620a52010-09-23 17:53:56 +0000207{
208 return false;
209}
210