IO mapper: Fix #1261: Supply location mapper with size computer.
This factored computeTypeLocationSize() out of needing the TIntermediate contents, and uses it to show how to know how many locations an object needs. However, it still does not do cross stage, or mixed location/no-location analysis.
This commit is contained in:
parent
d55fe86512
commit
c5215791f5
@ -2668,7 +2668,8 @@ void TGlslangToSpvTraverser::decorateStructType(const glslang::TType& type,
|
|||||||
builder.addMemberDecoration(spvType, member, spv::DecorationLocation, memberQualifier.layoutLocation);
|
builder.addMemberDecoration(spvType, member, spv::DecorationLocation, memberQualifier.layoutLocation);
|
||||||
|
|
||||||
if (qualifier.hasLocation()) // track for upcoming inheritance
|
if (qualifier.hasLocation()) // track for upcoming inheritance
|
||||||
locationOffset += glslangIntermediate->computeTypeLocationSize(glslangMember);
|
locationOffset += glslangIntermediate->computeTypeLocationSize(
|
||||||
|
glslangMember, glslangIntermediate->getStage());
|
||||||
|
|
||||||
// component, XFB, others
|
// component, XFB, others
|
||||||
if (glslangMember.getQualifier().hasComponent())
|
if (glslangMember.getQualifier().hasComponent())
|
||||||
|
|||||||
@ -6083,7 +6083,8 @@ void TParseContext::fixBlockLocations(const TSourceLoc& loc, TQualifier& qualifi
|
|||||||
memberQualifier.layoutLocation = nextLocation;
|
memberQualifier.layoutLocation = nextLocation;
|
||||||
memberQualifier.layoutComponent = TQualifier::layoutComponentEnd;
|
memberQualifier.layoutComponent = TQualifier::layoutComponentEnd;
|
||||||
}
|
}
|
||||||
nextLocation = memberQualifier.layoutLocation + intermediate.computeTypeLocationSize(*typeList[member].type);
|
nextLocation = memberQualifier.layoutLocation + intermediate.computeTypeLocationSize(
|
||||||
|
*typeList[member].type, language);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@ -353,7 +353,9 @@ struct TDefaultIoResolverBase : public glslang::TIoMapResolver
|
|||||||
{
|
{
|
||||||
TDefaultIoResolverBase(const TIntermediate &intermediate) :
|
TDefaultIoResolverBase(const TIntermediate &intermediate) :
|
||||||
intermediate(intermediate),
|
intermediate(intermediate),
|
||||||
nextUniformLocation(0)
|
nextUniformLocation(0),
|
||||||
|
nextInputLocation(0),
|
||||||
|
nextOutputLocation(0)
|
||||||
{ }
|
{ }
|
||||||
|
|
||||||
int getBaseBinding(TResourceType res, unsigned int set) const {
|
int getBaseBinding(TResourceType res, unsigned int set) const {
|
||||||
@ -446,7 +448,7 @@ struct TDefaultIoResolverBase : public glslang::TIoMapResolver
|
|||||||
{
|
{
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
int resolveInOutLocation(EShLanguage /*stage*/, const char* /*name*/, const TType& type, bool /*is_live*/) override
|
int resolveInOutLocation(EShLanguage stage, const char* /*name*/, const TType& type, bool /*is_live*/) override
|
||||||
{
|
{
|
||||||
// kick out of not doing this
|
// kick out of not doing this
|
||||||
if (!doAutoLocationMapping())
|
if (!doAutoLocationMapping())
|
||||||
@ -464,14 +466,15 @@ struct TDefaultIoResolverBase : public glslang::TIoMapResolver
|
|||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Placeholder.
|
// point to the right input or output location counter
|
||||||
// TODO: It would be nice to flesh this out using
|
int& nextLocation = type.getQualifier().isPipeInput() ? nextInputLocation : nextOutputLocation;
|
||||||
// intermediate->computeTypeLocationSize(type), or functions that call it like
|
|
||||||
// intermediate->addUsedLocation()
|
// Placeholder. This does not do proper cross-stage lining up, nor
|
||||||
// These in turn would want the intermediate, which is not available here, but
|
// work with mixed location/no-location declarations.
|
||||||
// is available in many places, and a lot of copying from it could be saved if
|
int location = nextLocation;
|
||||||
// it were just available.
|
nextLocation += TIntermediate::computeTypeLocationSize(type, stage);
|
||||||
return 0;
|
|
||||||
|
return location;
|
||||||
}
|
}
|
||||||
int resolveInOutComponent(EShLanguage /*stage*/, const char* /*name*/, const TType& /*type*/, bool /*is_live*/) override
|
int resolveInOutComponent(EShLanguage /*stage*/, const char* /*name*/, const TType& /*type*/, bool /*is_live*/) override
|
||||||
{
|
{
|
||||||
@ -492,6 +495,8 @@ struct TDefaultIoResolverBase : public glslang::TIoMapResolver
|
|||||||
protected:
|
protected:
|
||||||
const TIntermediate &intermediate;
|
const TIntermediate &intermediate;
|
||||||
int nextUniformLocation;
|
int nextUniformLocation;
|
||||||
|
int nextInputLocation;
|
||||||
|
int nextOutputLocation;
|
||||||
|
|
||||||
// Return descriptor set specific base if there is one, and the generic base otherwise.
|
// Return descriptor set specific base if there is one, and the generic base otherwise.
|
||||||
int selectBaseBinding(int base, int descriptorSetBase) const {
|
int selectBaseBinding(int base, int descriptorSetBase) const {
|
||||||
|
|||||||
@ -773,9 +773,9 @@ int TIntermediate::addUsedLocation(const TQualifier& qualifier, const TType& typ
|
|||||||
// Strip off the outer array dimension for those having an extra one.
|
// Strip off the outer array dimension for those having an extra one.
|
||||||
if (type.isArray() && qualifier.isArrayedIo(language)) {
|
if (type.isArray() && qualifier.isArrayedIo(language)) {
|
||||||
TType elementType(type, 0);
|
TType elementType(type, 0);
|
||||||
size = computeTypeLocationSize(elementType);
|
size = computeTypeLocationSize(elementType, language);
|
||||||
} else
|
} else
|
||||||
size = computeTypeLocationSize(type);
|
size = computeTypeLocationSize(type, language);
|
||||||
}
|
}
|
||||||
|
|
||||||
// Locations, and components within locations.
|
// Locations, and components within locations.
|
||||||
@ -907,7 +907,7 @@ bool TIntermediate::addUsedConstantId(int id)
|
|||||||
|
|
||||||
// Recursively figure out how many locations are used up by an input or output type.
|
// Recursively figure out how many locations are used up by an input or output type.
|
||||||
// Return the size of type, as measured by "locations".
|
// Return the size of type, as measured by "locations".
|
||||||
int TIntermediate::computeTypeLocationSize(const TType& type) const
|
int TIntermediate::computeTypeLocationSize(const TType& type, EShLanguage stage)
|
||||||
{
|
{
|
||||||
// "If the declared input is an array of size n and each element takes m locations, it will be assigned m * n
|
// "If the declared input is an array of size n and each element takes m locations, it will be assigned m * n
|
||||||
// consecutive locations..."
|
// consecutive locations..."
|
||||||
@ -916,9 +916,9 @@ int TIntermediate::computeTypeLocationSize(const TType& type) const
|
|||||||
TType elementType(type, 0);
|
TType elementType(type, 0);
|
||||||
if (type.isImplicitlySizedArray()) {
|
if (type.isImplicitlySizedArray()) {
|
||||||
// TODO: are there valid cases of having an implicitly-sized array with a location? If so, running this code too early.
|
// TODO: are there valid cases of having an implicitly-sized array with a location? If so, running this code too early.
|
||||||
return computeTypeLocationSize(elementType);
|
return computeTypeLocationSize(elementType, stage);
|
||||||
} else
|
} else
|
||||||
return type.getOuterArraySize() * computeTypeLocationSize(elementType);
|
return type.getOuterArraySize() * computeTypeLocationSize(elementType, stage);
|
||||||
}
|
}
|
||||||
|
|
||||||
// "The locations consumed by block and structure members are determined by applying the rules above
|
// "The locations consumed by block and structure members are determined by applying the rules above
|
||||||
@ -927,7 +927,7 @@ int TIntermediate::computeTypeLocationSize(const TType& type) const
|
|||||||
int size = 0;
|
int size = 0;
|
||||||
for (int member = 0; member < (int)type.getStruct()->size(); ++member) {
|
for (int member = 0; member < (int)type.getStruct()->size(); ++member) {
|
||||||
TType memberType(type, member);
|
TType memberType(type, member);
|
||||||
size += computeTypeLocationSize(memberType);
|
size += computeTypeLocationSize(memberType, stage);
|
||||||
}
|
}
|
||||||
return size;
|
return size;
|
||||||
}
|
}
|
||||||
@ -941,7 +941,7 @@ int TIntermediate::computeTypeLocationSize(const TType& type) const
|
|||||||
if (type.isScalar())
|
if (type.isScalar())
|
||||||
return 1;
|
return 1;
|
||||||
if (type.isVector()) {
|
if (type.isVector()) {
|
||||||
if (language == EShLangVertex && type.getQualifier().isPipeInput())
|
if (stage == EShLangVertex && type.getQualifier().isPipeInput())
|
||||||
return 1;
|
return 1;
|
||||||
if (type.getBasicType() == EbtDouble && type.getVectorSize() > 2)
|
if (type.getBasicType() == EbtDouble && type.getVectorSize() > 2)
|
||||||
return 2;
|
return 2;
|
||||||
@ -954,7 +954,7 @@ int TIntermediate::computeTypeLocationSize(const TType& type) const
|
|||||||
// for an n-element array of m-component vectors..."
|
// for an n-element array of m-component vectors..."
|
||||||
if (type.isMatrix()) {
|
if (type.isMatrix()) {
|
||||||
TType columnType(type, 0);
|
TType columnType(type, 0);
|
||||||
return type.getMatrixCols() * computeTypeLocationSize(columnType);
|
return type.getMatrixCols() * computeTypeLocationSize(columnType, stage);
|
||||||
}
|
}
|
||||||
|
|
||||||
assert(0);
|
assert(0);
|
||||||
|
|||||||
@ -575,7 +575,7 @@ public:
|
|||||||
int checkLocationRange(int set, const TIoRange& range, const TType&, bool& typeCollision);
|
int checkLocationRange(int set, const TIoRange& range, const TType&, bool& typeCollision);
|
||||||
int addUsedOffsets(int binding, int offset, int numOffsets);
|
int addUsedOffsets(int binding, int offset, int numOffsets);
|
||||||
bool addUsedConstantId(int id);
|
bool addUsedConstantId(int id);
|
||||||
int computeTypeLocationSize(const TType&) const;
|
static int computeTypeLocationSize(const TType&, EShLanguage);
|
||||||
|
|
||||||
bool setXfbBufferStride(int buffer, unsigned stride)
|
bool setXfbBufferStride(int buffer, unsigned stride)
|
||||||
{
|
{
|
||||||
|
|||||||
@ -1256,7 +1256,7 @@ int HlslParseContext::addFlattenedMember(const TVariable& variable, const TType&
|
|||||||
// inherited locations must be auto bumped, not replicated
|
// inherited locations must be auto bumped, not replicated
|
||||||
if (flattenData.nextLocation != TQualifier::layoutLocationEnd) {
|
if (flattenData.nextLocation != TQualifier::layoutLocationEnd) {
|
||||||
memberVariable->getWritableType().getQualifier().layoutLocation = flattenData.nextLocation;
|
memberVariable->getWritableType().getQualifier().layoutLocation = flattenData.nextLocation;
|
||||||
flattenData.nextLocation += intermediate.computeTypeLocationSize(memberVariable->getType());
|
flattenData.nextLocation += intermediate.computeTypeLocationSize(memberVariable->getType(), language);
|
||||||
nextOutLocation = std::max(nextOutLocation, flattenData.nextLocation);
|
nextOutLocation = std::max(nextOutLocation, flattenData.nextLocation);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -1536,9 +1536,9 @@ void HlslParseContext::assignToInterface(TVariable& variable)
|
|||||||
int size;
|
int size;
|
||||||
if (type.isArray() && qualifier.isArrayedIo(language)) {
|
if (type.isArray() && qualifier.isArrayedIo(language)) {
|
||||||
TType elementType(type, 0);
|
TType elementType(type, 0);
|
||||||
size = intermediate.computeTypeLocationSize(elementType);
|
size = intermediate.computeTypeLocationSize(elementType, language);
|
||||||
} else
|
} else
|
||||||
size = intermediate.computeTypeLocationSize(type);
|
size = intermediate.computeTypeLocationSize(type, language);
|
||||||
|
|
||||||
if (qualifier.storage == EvqVaryingIn) {
|
if (qualifier.storage == EvqVaryingIn) {
|
||||||
variable.getWritableType().getQualifier().layoutLocation = nextInLocation;
|
variable.getWritableType().getQualifier().layoutLocation = nextInLocation;
|
||||||
@ -8633,7 +8633,7 @@ void HlslParseContext::fixBlockLocations(const TSourceLoc& loc, TQualifier& qual
|
|||||||
memberQualifier.layoutComponent = 0;
|
memberQualifier.layoutComponent = 0;
|
||||||
}
|
}
|
||||||
nextLocation = memberQualifier.layoutLocation +
|
nextLocation = memberQualifier.layoutLocation +
|
||||||
intermediate.computeTypeLocationSize(*typeList[member].type);
|
intermediate.computeTypeLocationSize(*typeList[member].type, language);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user