Add reflection queries for thread local size and ssbo auto-binding

New command line option --shift-ssbo-binding mirrors --shift-ubo-binding, etc.

New reflection query getLocalSize(int dim) queries local size, e.g, CS threads.
This commit is contained in:
steve-lunarg 2017-02-21 17:19:08 -07:00
parent 5da1f038d8
commit 932bb5cc4e
11 changed files with 265 additions and 15 deletions

View file

@ -1557,6 +1557,7 @@ void TShader::setShiftSamplerBinding(unsigned int base) { intermediate->setShift
void TShader::setShiftTextureBinding(unsigned int base) { intermediate->setShiftTextureBinding(base); }
void TShader::setShiftImageBinding(unsigned int base) { intermediate->setShiftImageBinding(base); }
void TShader::setShiftUboBinding(unsigned int base) { intermediate->setShiftUboBinding(base); }
void TShader::setShiftSsboBinding(unsigned int base) { intermediate->setShiftSsboBinding(base); }
void TShader::setAutoMapBindings(bool map) { intermediate->setAutoMapBindings(map); }
void TShader::setFlattenUniformArrays(bool flatten) { intermediate->setFlattenUniformArrays(flatten); }
void TShader::setNoStorageFormat(bool useUnknownFormat) { intermediate->setNoStorageFormat(useUnknownFormat); }
@ -1784,6 +1785,7 @@ int TProgram::getAttributeType(int index) const { return reflection
const TType* TProgram::getAttributeTType(int index) const { return reflection->getAttribute(index).getType(); }
const TType* TProgram::getUniformTType(int index) const { return reflection->getUniform(index).getType(); }
const TType* TProgram::getUniformBlockTType(int index) const { return reflection->getUniformBlock(index).getType(); }
unsigned TProgram::getLocalSize(int dim) const { return reflection->getLocalSize(dim); }
void TProgram::dumpReflection() { reflection->dump(); }

View file

@ -122,7 +122,7 @@ public:
virtual void visitSymbol(TIntermSymbol* base)
{
if (base->getQualifier().storage == EvqUniform) {
if (base->getType().getQualifier().isUniformOrBuffer()) {
TVarEntryInfo ent = { base->getId(), base, !traverseAll };
TVarLiveMap::iterator at = std::lower_bound(varLiveList.begin(), varLiveList.end(), ent, TVarEntryInfo::TOrderById());
if (at != varLiveList.end() && at->id == ent.id)
@ -227,6 +227,7 @@ struct TDefaultIoResolver : public glslang::TIoMapResolver
int baseTextureBinding;
int baseImageBinding;
int baseUboBinding;
int baseSsboBinding;
bool doAutoMapping;
typedef std::vector<int> TSlotSet;
typedef std::unordered_map<int, TSlotSet> TSlotSetMap;
@ -281,8 +282,11 @@ struct TDefaultIoResolver : public glslang::TIoMapResolver
return checkEmpty(set, baseTextureBinding + type.getQualifier().layoutBinding);
}
if (type.getQualifier().isUniformOrBuffer())
if (type.getQualifier().storage == EvqUniform)
return checkEmpty(set, baseUboBinding + type.getQualifier().layoutBinding);
if (type.getQualifier().storage == EvqBuffer)
return checkEmpty(set, baseSsboBinding + type.getQualifier().layoutBinding);
}
return true;
}
@ -308,8 +312,11 @@ struct TDefaultIoResolver : public glslang::TIoMapResolver
return reserveSlot(set, baseTextureBinding + type.getQualifier().layoutBinding);
}
if (type.getQualifier().isUniformOrBuffer())
if (type.getQualifier().storage == EvqUniform)
return reserveSlot(set, baseUboBinding + type.getQualifier().layoutBinding);
if (type.getQualifier().storage == EvqBuffer)
return reserveSlot(set, baseSsboBinding + type.getQualifier().layoutBinding);
} else if (is_live && doAutoMapping) {
// find free slot, the caller did make sure it passes all vars with binding
// first and now all are passed that do not have a binding and needs one
@ -325,8 +332,11 @@ struct TDefaultIoResolver : public glslang::TIoMapResolver
return getFreeSlot(set, baseTextureBinding);
}
if (type.getQualifier().isUniformOrBuffer())
if (type.getQualifier().storage == EvqUniform)
return getFreeSlot(set, baseUboBinding);
if (type.getQualifier().storage == EvqBuffer)
return getFreeSlot(set, baseSsboBinding);
}
return -1;
@ -351,6 +361,7 @@ bool TIoMapper::addStage(EShLanguage stage, TIntermediate &intermediate, TInfoSi
intermediate.getShiftTextureBinding() == 0 &&
intermediate.getShiftImageBinding() == 0 &&
intermediate.getShiftUboBinding() == 0 &&
intermediate.getShiftSsboBinding() == 0 &&
intermediate.getAutoMapBindings() == false &&
resolver == nullptr)
return true;
@ -369,6 +380,7 @@ bool TIoMapper::addStage(EShLanguage stage, TIntermediate &intermediate, TInfoSi
defaultResolver.baseTextureBinding = intermediate.getShiftTextureBinding();
defaultResolver.baseImageBinding = intermediate.getShiftImageBinding();
defaultResolver.baseUboBinding = intermediate.getShiftUboBinding();
defaultResolver.baseSsboBinding = intermediate.getShiftSsboBinding();
defaultResolver.doAutoMapping = intermediate.getAutoMapBindings();
resolver = &defaultResolver;

View file

@ -174,6 +174,7 @@ public:
shiftTextureBinding(0),
shiftImageBinding(0),
shiftUboBinding(0),
shiftSsboBinding(0),
autoMapBindings(false),
flattenUniformArrays(false),
useUnknownFormat(false)
@ -207,6 +208,8 @@ public:
unsigned int getShiftImageBinding() const { return shiftImageBinding; }
void setShiftUboBinding(unsigned int shift) { shiftUboBinding = shift; }
unsigned int getShiftUboBinding() const { return shiftUboBinding; }
void setShiftSsboBinding(unsigned int shift) { shiftSsboBinding = shift; }
unsigned int getShiftSsboBinding() const { return shiftSsboBinding; }
void setAutoMapBindings(bool map) { autoMapBindings = map; }
bool getAutoMapBindings() const { return autoMapBindings; }
void setFlattenUniformArrays(bool flatten) { flattenUniformArrays = flatten; }
@ -485,6 +488,7 @@ protected:
unsigned int shiftTextureBinding;
unsigned int shiftImageBinding;
unsigned int shiftUboBinding;
unsigned int shiftSsboBinding;
bool autoMapBindings;
bool flattenUniformArrays;
bool useUnknownFormat;

View file

@ -696,14 +696,27 @@ void TReflectionTraverser::visitSymbol(TIntermSymbol* base)
// Implement TReflection methods.
//
// Track any required attribute reflection, such as compute shader numthreads.
//
void TReflection::buildAttributeReflection(EShLanguage stage, const TIntermediate& intermediate)
{
if (stage == EShLangCompute) {
// Remember thread dimensions
for (int dim=0; dim<3; ++dim)
localSize[dim] = intermediate.getLocalSize(dim);
}
}
// Merge live symbols from 'intermediate' into the existing reflection database.
//
// Returns false if the input is too malformed to do this.
bool TReflection::addStage(EShLanguage, const TIntermediate& intermediate)
bool TReflection::addStage(EShLanguage stage, const TIntermediate& intermediate)
{
if (intermediate.getNumEntryPoints() != 1 || intermediate.isRecursive())
return false;
buildAttributeReflection(stage, intermediate);
TReflectionTraverser it(intermediate, *this);
// put the entry point on the list of functions to process
@ -736,6 +749,16 @@ void TReflection::dump()
indexToAttribute[i].dump();
printf("\n");
if (getLocalSize(0) > 1) {
static const char* axis[] = { "X", "Y", "Z" };
for (int dim=0; dim<3; ++dim)
if (getLocalSize(dim) > 1)
printf("Local size %s: %d\n", axis[dim], getLocalSize(dim));
printf("\n");
}
// printf("Live names\n");
// for (TNameToIndex::const_iterator it = nameToIndex.begin(); it != nameToIndex.end(); ++it)
// printf("%s: %d\n", it->first.c_str(), it->second);

View file

@ -89,7 +89,12 @@ protected:
// The full reflection database
class TReflection {
public:
TReflection() : badReflection(TObjectReflection::badReflection()) { }
TReflection() : badReflection(TObjectReflection::badReflection())
{
for (int dim=0; dim<3; ++dim)
localSize[dim] = 0;
}
virtual ~TReflection() {}
// grow the reflection stage by stage
@ -135,11 +140,16 @@ public:
return it->second;
}
// Thread local size
unsigned getLocalSize(int dim) const { return dim <= 2 ? localSize[dim] : 0; }
void dump();
protected:
friend class glslang::TReflectionTraverser;
void buildAttributeReflection(EShLanguage, const TIntermediate&);
// Need a TString hash: typedef std::unordered_map<TString, int> TNameToIndex;
typedef std::map<TString, int> TNameToIndex;
typedef std::vector<TObjectReflection> TMapIndexToReflection;
@ -149,6 +159,8 @@ protected:
TMapIndexToReflection indexToUniform;
TMapIndexToReflection indexToUniformBlock;
TMapIndexToReflection indexToAttribute;
unsigned int localSize[3];
};
} // end namespace glslang

View file

@ -310,6 +310,7 @@ public:
void setShiftTextureBinding(unsigned int base);
void setShiftImageBinding(unsigned int base);
void setShiftUboBinding(unsigned int base);
void setShiftSsboBinding(unsigned int base);
void setAutoMapBindings(bool map);
void setFlattenUniformArrays(bool flatten);
void setNoStorageFormat(bool useUnknownFormat);
@ -514,6 +515,7 @@ public:
int getUniformBufferOffset(int index) const; // can be used for glGetActiveUniformsiv(GL_UNIFORM_OFFSET)
int getUniformArraySize(int index) const; // can be used for glGetActiveUniformsiv(GL_UNIFORM_SIZE)
int getNumLiveAttributes() const; // can be used for glGetProgramiv(GL_ACTIVE_ATTRIBUTES)
unsigned getLocalSize(int dim) const; // return dim'th local size
const char *getAttributeName(int index) const; // can be used for glGetActiveAttrib()
int getAttributeType(int index) const; // can be used for glGetActiveAttrib()
const TType* getUniformTType(int index) const; // returns a TType*