Non-functional: correctly do GL_EXT_buffer_reference2 semantic checking
See #2366 for detail.
This commit is contained in:
parent
6c37bbbb03
commit
d8daeb4323
@ -2,8 +2,12 @@ spv.bufferhandle17_Errors.frag
|
|||||||
ERROR: 0:11: 'qualifier' : variables with reference type can't have qualifier 'const'
|
ERROR: 0:11: 'qualifier' : variables with reference type can't have qualifier 'const'
|
||||||
ERROR: 0:16: 'qualifier' : variables with reference type can't have qualifier 'const'
|
ERROR: 0:16: 'qualifier' : variables with reference type can't have qualifier 'const'
|
||||||
ERROR: 0:18: '==' : can't use with reference types
|
ERROR: 0:18: '==' : can't use with reference types
|
||||||
|
ERROR: 0:18: 'buffer reference math' : required extension not requested: GL_EXT_buffer_reference2
|
||||||
|
ERROR: 0:18: '==' : wrong operand types: no operation '==' exists that takes a left-hand operand of type ' temp reference' and a right operand of type ' temp reference' (or there is no acceptable conversion)
|
||||||
ERROR: 0:19: '!=' : can't use with reference types
|
ERROR: 0:19: '!=' : can't use with reference types
|
||||||
ERROR: 4 compilation errors. No code generated.
|
ERROR: 0:19: 'buffer reference math' : required extension not requested: GL_EXT_buffer_reference2
|
||||||
|
ERROR: 0:19: '!=' : wrong operand types: no operation '!=' exists that takes a left-hand operand of type ' temp reference' and a right operand of type ' temp reference' (or there is no acceptable conversion)
|
||||||
|
ERROR: 8 compilation errors. No code generated.
|
||||||
|
|
||||||
|
|
||||||
SPIR-V is not generated for failed compile or link
|
SPIR-V is not generated for failed compile or link
|
||||||
|
@ -120,7 +120,7 @@ TIntermTyped* TIntermediate::addBinaryMath(TOperator op, TIntermTyped* left, TIn
|
|||||||
return nullptr;
|
return nullptr;
|
||||||
|
|
||||||
// Convert "reference +/- int" and "reference - reference" to integer math
|
// Convert "reference +/- int" and "reference - reference" to integer math
|
||||||
if ((op == EOpAdd || op == EOpSub) && extensionRequested(E_GL_EXT_buffer_reference2)) {
|
if (op == EOpAdd || op == EOpSub) {
|
||||||
|
|
||||||
// No addressing math on struct with unsized array.
|
// No addressing math on struct with unsized array.
|
||||||
if ((left->isReference() && left->getType().getReferentType()->containsUnsizedArray()) ||
|
if ((left->isReference() && left->getType().getReferentType()->containsUnsizedArray()) ||
|
||||||
@ -140,41 +140,42 @@ TIntermTyped* TIntermediate::addBinaryMath(TOperator op, TIntermTyped* left, TIn
|
|||||||
node = addBuiltInFunctionCall(loc, EOpConvUint64ToPtr, true, node, referenceType);
|
node = addBuiltInFunctionCall(loc, EOpConvUint64ToPtr, true, node, referenceType);
|
||||||
return node;
|
return node;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (op == EOpAdd && right->isReference() && isTypeInt(left->getBasicType())) {
|
|
||||||
const TType& referenceType = right->getType();
|
|
||||||
TIntermConstantUnion* size = addConstantUnion((unsigned long long)computeBufferReferenceTypeSize(right->getType()), loc, true);
|
|
||||||
right = addBuiltInFunctionCall(loc, EOpConvPtrToUint64, true, right, TType(EbtUint64));
|
|
||||||
|
|
||||||
left = createConversion(EbtInt64, left);
|
|
||||||
left = addBinaryMath(EOpMul, left, size, loc);
|
|
||||||
|
|
||||||
TIntermTyped *node = addBinaryMath(op, left, right, loc);
|
|
||||||
node = addBuiltInFunctionCall(loc, EOpConvUint64ToPtr, true, node, referenceType);
|
|
||||||
return node;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (op == EOpSub && left->isReference() && right->isReference()) {
|
|
||||||
TIntermConstantUnion* size = addConstantUnion((long long)computeBufferReferenceTypeSize(left->getType()), loc, true);
|
|
||||||
|
|
||||||
left = addBuiltInFunctionCall(loc, EOpConvPtrToUint64, true, left, TType(EbtUint64));
|
|
||||||
right = addBuiltInFunctionCall(loc, EOpConvPtrToUint64, true, right, TType(EbtUint64));
|
|
||||||
|
|
||||||
left = addBuiltInFunctionCall(loc, EOpConvUint64ToInt64, true, left, TType(EbtInt64));
|
|
||||||
right = addBuiltInFunctionCall(loc, EOpConvUint64ToInt64, true, right, TType(EbtInt64));
|
|
||||||
|
|
||||||
left = addBinaryMath(EOpSub, left, right, loc);
|
|
||||||
|
|
||||||
TIntermTyped *node = addBinaryMath(EOpDiv, left, size, loc);
|
|
||||||
return node;
|
|
||||||
}
|
|
||||||
|
|
||||||
// No other math operators supported on references
|
|
||||||
if (left->isReference() || right->isReference()) {
|
|
||||||
return nullptr;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (op == EOpAdd && right->isReference() && isTypeInt(left->getBasicType())) {
|
||||||
|
const TType& referenceType = right->getType();
|
||||||
|
TIntermConstantUnion* size =
|
||||||
|
addConstantUnion((unsigned long long)computeBufferReferenceTypeSize(right->getType()), loc, true);
|
||||||
|
right = addBuiltInFunctionCall(loc, EOpConvPtrToUint64, true, right, TType(EbtUint64));
|
||||||
|
|
||||||
|
left = createConversion(EbtInt64, left);
|
||||||
|
left = addBinaryMath(EOpMul, left, size, loc);
|
||||||
|
|
||||||
|
TIntermTyped *node = addBinaryMath(op, left, right, loc);
|
||||||
|
node = addBuiltInFunctionCall(loc, EOpConvUint64ToPtr, true, node, referenceType);
|
||||||
|
return node;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (op == EOpSub && left->isReference() && right->isReference()) {
|
||||||
|
TIntermConstantUnion* size =
|
||||||
|
addConstantUnion((long long)computeBufferReferenceTypeSize(left->getType()), loc, true);
|
||||||
|
|
||||||
|
left = addBuiltInFunctionCall(loc, EOpConvPtrToUint64, true, left, TType(EbtUint64));
|
||||||
|
right = addBuiltInFunctionCall(loc, EOpConvPtrToUint64, true, right, TType(EbtUint64));
|
||||||
|
|
||||||
|
left = addBuiltInFunctionCall(loc, EOpConvUint64ToInt64, true, left, TType(EbtInt64));
|
||||||
|
right = addBuiltInFunctionCall(loc, EOpConvUint64ToInt64, true, right, TType(EbtInt64));
|
||||||
|
|
||||||
|
left = addBinaryMath(EOpSub, left, right, loc);
|
||||||
|
|
||||||
|
TIntermTyped *node = addBinaryMath(EOpDiv, left, size, loc);
|
||||||
|
return node;
|
||||||
|
}
|
||||||
|
|
||||||
|
// No other math operators supported on references
|
||||||
|
if (left->isReference() || right->isReference())
|
||||||
|
return nullptr;
|
||||||
|
|
||||||
// Try converting the children's base types to compatible types.
|
// Try converting the children's base types to compatible types.
|
||||||
auto children = addConversion(op, left, right);
|
auto children = addConversion(op, left, right);
|
||||||
left = std::get<0>(children);
|
left = std::get<0>(children);
|
||||||
@ -290,9 +291,7 @@ TIntermTyped* TIntermediate::addAssign(TOperator op, TIntermTyped* left, TInterm
|
|||||||
// Convert "reference += int" to "reference = reference + int". We need this because the
|
// Convert "reference += int" to "reference = reference + int". We need this because the
|
||||||
// "reference + int" calculation involves a cast back to the original type, which makes it
|
// "reference + int" calculation involves a cast back to the original type, which makes it
|
||||||
// not an lvalue.
|
// not an lvalue.
|
||||||
if ((op == EOpAddAssign || op == EOpSubAssign) && left->isReference() &&
|
if ((op == EOpAddAssign || op == EOpSubAssign) && left->isReference()) {
|
||||||
extensionRequested(E_GL_EXT_buffer_reference2)) {
|
|
||||||
|
|
||||||
if (!(right->getType().isScalar() && right->getType().isIntegerDomain()))
|
if (!(right->getType().isScalar() && right->getType().isIntegerDomain()))
|
||||||
return nullptr;
|
return nullptr;
|
||||||
|
|
||||||
|
@ -751,8 +751,11 @@ TIntermTyped* TParseContext::handleBinaryMath(const TSourceLoc& loc, const char*
|
|||||||
}
|
}
|
||||||
|
|
||||||
TIntermTyped* result = nullptr;
|
TIntermTyped* result = nullptr;
|
||||||
if (allowed)
|
if (allowed) {
|
||||||
|
if ((left->isReference() || right->isReference()))
|
||||||
|
requireExtensions(loc, 1, &E_GL_EXT_buffer_reference2, "buffer reference math");
|
||||||
result = intermediate.addBinaryMath(op, left, right, loc);
|
result = intermediate.addBinaryMath(op, left, right, loc);
|
||||||
|
}
|
||||||
|
|
||||||
if (result == nullptr)
|
if (result == nullptr)
|
||||||
binaryOpError(loc, str, left->getCompleteString(), right->getCompleteString());
|
binaryOpError(loc, str, left->getCompleteString(), right->getCompleteString());
|
||||||
@ -1680,6 +1683,14 @@ TIntermTyped* TParseContext::addOutputArgumentConversions(const TFunction& funct
|
|||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
|
TIntermTyped* TParseContext::addAssign(const TSourceLoc& loc, TOperator op, TIntermTyped* left, TIntermTyped* right)
|
||||||
|
{
|
||||||
|
if ((op == EOpAddAssign || op == EOpSubAssign) && left->isReference())
|
||||||
|
requireExtensions(loc, 1, &E_GL_EXT_buffer_reference2, "+= and -= on a buffer reference");
|
||||||
|
|
||||||
|
return intermediate.addAssign(op, left, right, loc);
|
||||||
|
}
|
||||||
|
|
||||||
void TParseContext::memorySemanticsCheck(const TSourceLoc& loc, const TFunction& fnCandidate, const TIntermOperator& callNode)
|
void TParseContext::memorySemanticsCheck(const TSourceLoc& loc, const TFunction& fnCandidate, const TIntermOperator& callNode)
|
||||||
{
|
{
|
||||||
const TIntermSequence* argp = &callNode.getAsAggregate()->getSequence();
|
const TIntermSequence* argp = &callNode.getAsAggregate()->getSequence();
|
||||||
|
@ -328,6 +328,7 @@ public:
|
|||||||
TIntermTyped* handleLengthMethod(const TSourceLoc&, TFunction*, TIntermNode*);
|
TIntermTyped* handleLengthMethod(const TSourceLoc&, TFunction*, TIntermNode*);
|
||||||
void addInputArgumentConversions(const TFunction&, TIntermNode*&) const;
|
void addInputArgumentConversions(const TFunction&, TIntermNode*&) const;
|
||||||
TIntermTyped* addOutputArgumentConversions(const TFunction&, TIntermAggregate&) const;
|
TIntermTyped* addOutputArgumentConversions(const TFunction&, TIntermAggregate&) const;
|
||||||
|
TIntermTyped* addAssign(const TSourceLoc&, TOperator op, TIntermTyped* left, TIntermTyped* right);
|
||||||
void builtInOpCheck(const TSourceLoc&, const TFunction&, TIntermOperator&);
|
void builtInOpCheck(const TSourceLoc&, const TFunction&, TIntermOperator&);
|
||||||
void nonOpBuiltInCheck(const TSourceLoc&, const TFunction&, TIntermAggregate&);
|
void nonOpBuiltInCheck(const TSourceLoc&, const TFunction&, TIntermAggregate&);
|
||||||
void userFunctionCallCheck(const TSourceLoc&, TIntermAggregate&);
|
void userFunctionCallCheck(const TSourceLoc&, TIntermAggregate&);
|
||||||
|
@ -778,7 +778,7 @@ assignment_expression
|
|||||||
parseContext.specializationCheck($2.loc, $1->getType(), "=");
|
parseContext.specializationCheck($2.loc, $1->getType(), "=");
|
||||||
parseContext.lValueErrorCheck($2.loc, "assign", $1);
|
parseContext.lValueErrorCheck($2.loc, "assign", $1);
|
||||||
parseContext.rValueErrorCheck($2.loc, "assign", $3);
|
parseContext.rValueErrorCheck($2.loc, "assign", $3);
|
||||||
$$ = parseContext.intermediate.addAssign($2.op, $1, $3, $2.loc);
|
$$ = parseContext.addAssign($2.loc, $2.op, $1, $3);
|
||||||
if ($$ == 0) {
|
if ($$ == 0) {
|
||||||
parseContext.assignError($2.loc, "assign", $1->getCompleteString(), $3->getCompleteString());
|
parseContext.assignError($2.loc, "assign", $1->getCompleteString(), $3->getCompleteString());
|
||||||
$$ = $1;
|
$$ = $1;
|
||||||
|
@ -778,7 +778,7 @@ assignment_expression
|
|||||||
parseContext.specializationCheck($2.loc, $1->getType(), "=");
|
parseContext.specializationCheck($2.loc, $1->getType(), "=");
|
||||||
parseContext.lValueErrorCheck($2.loc, "assign", $1);
|
parseContext.lValueErrorCheck($2.loc, "assign", $1);
|
||||||
parseContext.rValueErrorCheck($2.loc, "assign", $3);
|
parseContext.rValueErrorCheck($2.loc, "assign", $3);
|
||||||
$$ = parseContext.intermediate.addAssign($2.op, $1, $3, $2.loc);
|
$$ = parseContext.addAssign($2.loc, $2.op, $1, $3);
|
||||||
if ($$ == 0) {
|
if ($$ == 0) {
|
||||||
parseContext.assignError($2.loc, "assign", $1->getCompleteString(), $3->getCompleteString());
|
parseContext.assignError($2.loc, "assign", $1->getCompleteString(), $3->getCompleteString());
|
||||||
$$ = $1;
|
$$ = $1;
|
||||||
@ -3885,4 +3885,3 @@ single_attribute
|
|||||||
|
|
||||||
|
|
||||||
%%
|
%%
|
||||||
|
|
||||||
|
File diff suppressed because it is too large
Load Diff
@ -30,8 +30,8 @@
|
|||||||
This special exception was added by the Free Software Foundation in
|
This special exception was added by the Free Software Foundation in
|
||||||
version 2.2 of Bison. */
|
version 2.2 of Bison. */
|
||||||
|
|
||||||
#ifndef YY_YY_GLSLANG_TAB_CPP_H_INCLUDED
|
#ifndef YY_YY_MACHINEINDEPENDENT_GLSLANG_TAB_CPP_H_INCLUDED
|
||||||
# define YY_YY_GLSLANG_TAB_CPP_H_INCLUDED
|
# define YY_YY_MACHINEINDEPENDENT_GLSLANG_TAB_CPP_H_INCLUDED
|
||||||
/* Debug traces. */
|
/* Debug traces. */
|
||||||
#ifndef YYDEBUG
|
#ifndef YYDEBUG
|
||||||
# define YYDEBUG 1
|
# define YYDEBUG 1
|
||||||
@ -470,7 +470,7 @@ extern int yydebug;
|
|||||||
|
|
||||||
union YYSTYPE
|
union YYSTYPE
|
||||||
{
|
{
|
||||||
#line 97 "glslang.y" /* yacc.c:1909 */
|
#line 97 "MachineIndependent/glslang.y" /* yacc.c:1909 */
|
||||||
|
|
||||||
struct {
|
struct {
|
||||||
glslang::TSourceLoc loc;
|
glslang::TSourceLoc loc;
|
||||||
@ -506,7 +506,7 @@ union YYSTYPE
|
|||||||
glslang::TArraySizes* typeParameters;
|
glslang::TArraySizes* typeParameters;
|
||||||
} interm;
|
} interm;
|
||||||
|
|
||||||
#line 510 "glslang_tab.cpp.h" /* yacc.c:1909 */
|
#line 510 "MachineIndependent/glslang_tab.cpp.h" /* yacc.c:1909 */
|
||||||
};
|
};
|
||||||
|
|
||||||
typedef union YYSTYPE YYSTYPE;
|
typedef union YYSTYPE YYSTYPE;
|
||||||
@ -518,4 +518,4 @@ typedef union YYSTYPE YYSTYPE;
|
|||||||
|
|
||||||
int yyparse (glslang::TParseContext* pParseContext);
|
int yyparse (glslang::TParseContext* pParseContext);
|
||||||
|
|
||||||
#endif /* !YY_YY_GLSLANG_TAB_CPP_H_INCLUDED */
|
#endif /* !YY_YY_MACHINEINDEPENDENT_GLSLANG_TAB_CPP_H_INCLUDED */
|
||||||
|
Loading…
x
Reference in New Issue
Block a user