Qt 6.x
The Qt SDK
Loading...
Searching...
No Matches
glslsemantic.cpp
Go to the documentation of this file.
1// Copyright (C) 2021 The Qt Company Ltd.
2// SPDX-License-Identifier: LicenseRef-Qt-Commercial OR GPL-3.0-only
3
4#include "glslsemantic_p.h"
5#include "glslengine_p.h"
6#include "glslparser_p.h"
7#include "glslsymbols_p.h"
8#include "glsltypes_p.h"
9#include <QDebug>
10
12
13using namespace GLSL;
14
16 : _engine(nullptr)
17 , _scope(nullptr)
18 , _type(nullptr)
19{
20}
21
23{
24}
25
27{
28 Engine *previousEngine = _engine;
29 _engine = engine;
30 return previousEngine;
31}
32
34{
35 Scope *previousScope = _scope;
36 _scope = scope;
37 return previousScope;
38}
39
41{
43 std::swap(_expr, r);
44 accept(ast);
45 std::swap(_expr, r);
46 return r;
47}
48
50{
51 accept(ast);
52}
53
55{
56 const Type *t = _engine->undefinedType();
57 std::swap(_type, t);
58 accept(ast);
59 std::swap(_type, t);
60 return t;
61}
62
64{
65 accept(ast);
66}
67
69{
70 Engine *previousEngine = switchEngine(engine);
71 Scope *previousScope = switchScope(globalScope);
72 if (ast) {
73 for (List<DeclarationAST *> *it = ast->declarations; it; it = it->next) {
74 DeclarationAST *decl = it->value;
75 declaration(decl);
76 }
77 }
78 (void) switchScope(previousScope);
79 (void) switchEngine(previousEngine);
80}
81
83{
84 ExprResult result(engine->undefinedType());
85 if (ast && scope) {
86 Engine *previousEngine = switchEngine(engine);
87 Scope *previousScope = switchScope(scope);
88 result = expression(ast);
89 (void) switchScope(previousScope);
90 (void) switchEngine(previousEngine);
91 }
92 return result;
93}
94
96{
98 if (ast) {
99 if (ast->name) {
100 if (Symbol *s = _scope->lookup(*ast->name)) {
101 if (s->asOverloadSet() != nullptr || s->asFunction() != nullptr)
102 result.type = s->type();
103 else
104 _engine->error(ast->lineno, QString::fromLatin1("`%1' cannot be used as a function").arg(*ast->name));
105 } else {
106 _engine->error(ast->lineno, QString::fromLatin1("`%1' was not declared in this scope").arg(*ast->name));
107 }
108 } else if (ast->type) {
109 const Type *ty = type(ast->type);
110 result.type = ty;
111 }
112 }
113
114 return result;
115}
116
118{
119 // ast->name
120 const Type *ty = type(ast->type);
122 if (ast->name)
123 name = *ast->name;
124 return _engine->newVariable(_scope, name, ty);
125}
126
128{
129 const Type *ty = type(ast->type);
131 if (ast->name)
132 name = *ast->name;
133 Argument *arg = _engine->newArgument(fun, name, ty);
134 fun->addArgument(arg);
135}
136
138{
139 Q_UNUSED(ast)
140 Q_ASSERT(!"unreachable");
141 return false;
142}
143
145{
146 Q_UNUSED(ast)
147 Q_ASSERT(!"unreachable");
148 return false;
149}
150
152{
153 Q_UNUSED(ast)
154 Q_ASSERT(!"unreachable");
155 return false;
156}
157
158
159// expressions
161{
162 if (ast->name) {
163 if (Symbol *s = _scope->lookup(*ast->name))
164 _expr.type = s->type();
165 else
166 _engine->error(ast->lineno, QString::fromLatin1("`%1' was not declared in this scope").arg(*ast->name));
167 }
168 return false;
169}
170
172{
173 if (ast->value) {
174 _expr.isConstant = true;
175
176 if (ast->value->at(0) == QLatin1Char('t') && *ast->value == QLatin1String("true"))
177 _expr.type = _engine->boolType();
178 else if (ast->value->at(0) == QLatin1Char('f') && *ast->value == QLatin1String("false"))
179 _expr.type = _engine->boolType();
180 else if (ast->value->endsWith(QLatin1Char('u')) || ast->value->endsWith(QLatin1Char('U')))
181 _expr.type = _engine->uintType();
182 else if (ast->value->endsWith(QLatin1String("lf")) || ast->value->endsWith(QLatin1String("LF")))
183 _expr.type = _engine->doubleType();
184 else if (ast->value->endsWith(QLatin1Char('f')) || ast->value->endsWith(QLatin1Char('F')) || ast->value->contains(QLatin1Char('.')))
185 _expr.type = _engine->floatType();
186 else
187 _expr.type = _engine->intType();
188 }
189 return false;
190}
191
193{
196 _expr.isConstant = left.isConstant && right.isConstant;
197 switch (ast->kind) {
199 if (left.type) {
200 if (const IndexType *idxType = left.type->asIndexType())
201 _expr = idxType->indexElementType();
202 else
203 _engine->error(ast->lineno, QString::fromLatin1("Invalid type `%1' for array subscript").arg(left.type->toString()));
204 }
205 break;
206
209 case AST::Kind_Divide:
210 case AST::Kind_Plus:
211 case AST::Kind_Minus:
214 _expr.type = left.type; // ### not exactly
215 break;
216
221 case AST::Kind_Equal:
229 _expr.type = _engine->boolType();
230 break;
231
232 case AST::Kind_Comma:
233 _expr = right;
234 break;
235 }
236
237 return false;
238}
239
241{
242 ExprResult expr = expression(ast->expr);
243 _expr = expr;
244 return false;
245}
246
248{
250 ExprResult second = expression(ast->second);
251 ExprResult third = expression(ast->third);
252 _expr.isConstant = first.isConstant && second.isConstant && third.isConstant;
253 _expr.type = second.type;
254 return false;
255}
256
258{
261 return false;
262}
263
265{
266 ExprResult expr = expression(ast->expr);
267 if (expr.type && ast->field) {
268 if (const VectorType *vecTy = expr.type->asVectorType()) {
269 if (Symbol *s = vecTy->find(*ast->field))
270 _expr.type = s->type();
271 else
272 _engine->error(ast->lineno, QString::fromLatin1("`%1' has no member named `%2'").arg(vecTy->name()).arg(*ast->field));
273 } else if (const Struct *structTy = expr.type->asStructType()) {
274 if (Symbol *s = structTy->find(*ast->field))
275 _expr.type = s->type();
276 else
277 _engine->error(ast->lineno, QString::fromLatin1("`%1' has no member named `%2'").arg(structTy->name()).arg(*ast->field));
278 } else {
279 _engine->error(ast->lineno, QString::fromLatin1("Requested for member `%1', in a non class or vec instance").arg(*ast->field));
280 }
281 }
282 return false;
283}
284
285bool Semantic::implicitCast(const Type *type, const Type *target) const
286{
287 if (! (type && target)) {
288 return false;
289 } else if (type->isEqualTo(target)) {
290 return true;
291 } else if (target->asUIntType() != nullptr) {
292 return type->asIntType() != nullptr;
293 } else if (target->asFloatType() != nullptr) {
294 return type->asIntType() != nullptr ||
295 type->asUIntType() != nullptr;
296 } else if (target->asDoubleType() != nullptr) {
297 return type->asIntType() != nullptr ||
298 type->asUIntType() != nullptr ||
299 type->asFloatType() != nullptr;
300 } else if (const VectorType *targetVecTy = target->asVectorType()) {
301 if (const VectorType *vecTy = type->asVectorType()) {
302 if (targetVecTy->dimension() == vecTy->dimension()) {
303 const Type *targetElementType = targetVecTy->elementType();
304 const Type *elementType = vecTy->elementType();
305
306 if (targetElementType->asUIntType() != nullptr) {
307 // uvec* -> ivec*
308 return elementType->asIntType() != nullptr;
309 } else if (targetElementType->asFloatType() != nullptr) {
310 // vec* -> ivec* | uvec*
311 return elementType->asIntType() != nullptr ||
312 elementType->asUIntType() != nullptr;
313 } else if (targetElementType->asDoubleType() != nullptr) {
314 // dvec* -> ivec* | uvec* | fvec*
315 return elementType->asIntType() != nullptr ||
316 elementType->asUIntType() != nullptr ||
317 elementType->asFloatType() != nullptr;
318 }
319 }
320 }
321 } else if (const MatrixType *targetMatTy = target->asMatrixType()) {
322 if (const MatrixType *matTy = type->asMatrixType()) {
323 if (targetMatTy->columns() == matTy->columns() &&
324 targetMatTy->rows() == matTy->rows()) {
325 const Type *targetElementType = targetMatTy->elementType();
326 const Type *elementType = matTy->elementType();
327
328 if (targetElementType->asDoubleType() != nullptr) {
329 // dmat* -> mat*
330 return elementType->asFloatType() != nullptr;
331 }
332 }
333 }
334 }
335
336 return false;
337}
338
340{
341 ExprResult expr = expression(ast->expr);
343 QVector<ExprResult> actuals;
344 for (List<ExpressionAST *> *it = ast->arguments; it; it = it->next) {
345 ExprResult arg = expression(it->value);
346 actuals.append(arg);
347 }
348 if (id.isValid()) {
349 if (const Function *funTy = id.type->asFunctionType()) {
350 if (actuals.size() < funTy->argumentCount())
351 _engine->error(ast->lineno, QString::fromLatin1("not enough arguments"));
352 else if (actuals.size() > funTy->argumentCount())
353 _engine->error(ast->lineno, QString::fromLatin1("too many arguments"));
354 _expr.type = funTy->returnType();
355 } else if (const OverloadSet *overloads = id.type->asOverloadSetType()) {
356 QVector<Function *> candidates;
357 foreach (Function *f, overloads->functions()) {
358 if (f->argumentCount() == actuals.size()) {
359 int argc = 0;
360 for (; argc < actuals.size(); ++argc) {
361 const Type *actualTy = actuals.at(argc).type;
362 const Type *argumentTy = f->argumentAt(argc)->type();
363 if (! implicitCast(actualTy, argumentTy))
364 break;
365 }
366
367 if (argc == actuals.size())
368 candidates.append(f);
369 }
370 }
371
372 if (candidates.isEmpty()) {
373 // ### error, unresolved call.
374 Q_ASSERT(! overloads->functions().isEmpty());
375
376 _expr.type = overloads->functions().constFirst()->returnType();
377 } else {
378 _expr.type = candidates.constFirst()->returnType();
379
380 if (candidates.size() != 1) {
381 // ### error, ambiguous call
382 }
383 }
384 } else {
385 // called as constructor, e.g. vec2(a, b)
386 _expr.type = id.type;
387 }
388 }
389
390 return false;
391}
392
394{
395 const Type *ty = type(ast->type);
396 Q_UNUSED(ty)
397 // ast->name
398 ExprResult initializer = expression(ast->initializer);
399 return false;
400}
401
402
403// statements
405{
406 ExprResult expr = expression(ast->expr);
407 return false;
408}
409
411{
412 Block *block = _engine->newBlock(_scope);
413 Scope *previousScope = switchScope(block);
414 ast->symbol = block;
415 for (List<StatementAST *> *it = ast->statements; it; it = it->next) {
416 StatementAST *stmt = it->value;
417 statement(stmt);
418 }
419 (void) switchScope(previousScope);
420 return false;
421}
422
424{
426 statement(ast->thenClause);
427 statement(ast->elseClause);
428 return false;
429}
430
432{
434 statement(ast->body);
435 return false;
436}
437
439{
440 statement(ast->body);
442 return false;
443}
444
446{
447 statement(ast->init);
450 statement(ast->body);
451 return false;
452}
453
455{
456 Q_UNUSED(ast)
457 return false;
458}
459
461{
462 ExprResult expr = expression(ast->expr);
463 return false;
464}
465
467{
468 ExprResult expr = expression(ast->expr);
469 statement(ast->body);
470 return false;
471}
472
474{
475 ExprResult expr = expression(ast->expr);
476 return false;
477}
478
480{
481 declaration(ast->decl);
482 return false;
483}
484
485
486// types
488{
489 switch (ast->token) {
490 case Parser::T_VOID:
491 _type = _engine->voidType();
492 break;
493
494 case Parser::T_BOOL:
495 _type = _engine->boolType();
496 break;
497
498 case Parser::T_INT:
499 _type = _engine->intType();
500 break;
501
502 case Parser::T_UINT:
503 _type = _engine->uintType();
504 break;
505
506 case Parser::T_FLOAT:
507 _type = _engine->floatType();
508 break;
509
510 case Parser::T_DOUBLE:
511 _type = _engine->doubleType();
512 break;
513
514 // bvec
515 case Parser::T_BVEC2:
516 _type = _engine->vectorType(_engine->boolType(), 2);
517 break;
518
519 case Parser::T_BVEC3:
520 _type = _engine->vectorType(_engine->boolType(), 3);
521 break;
522
523 case Parser::T_BVEC4:
524 _type = _engine->vectorType(_engine->boolType(), 4);
525 break;
526
527 // ivec
528 case Parser::T_IVEC2:
529 _type = _engine->vectorType(_engine->intType(), 2);
530 break;
531
532 case Parser::T_IVEC3:
533 _type = _engine->vectorType(_engine->intType(), 3);
534 break;
535
536 case Parser::T_IVEC4:
537 _type = _engine->vectorType(_engine->intType(), 4);
538 break;
539
540 // uvec
541 case Parser::T_UVEC2:
542 _type = _engine->vectorType(_engine->uintType(), 2);
543 break;
544
545 case Parser::T_UVEC3:
546 _type = _engine->vectorType(_engine->uintType(), 3);
547 break;
548
549 case Parser::T_UVEC4:
550 _type = _engine->vectorType(_engine->uintType(), 4);
551 break;
552
553 // vec
554 case Parser::T_VEC2:
555 _type = _engine->vectorType(_engine->floatType(), 2);
556 break;
557
558 case Parser::T_VEC3:
559 _type = _engine->vectorType(_engine->floatType(), 3);
560 break;
561
562 case Parser::T_VEC4:
563 _type = _engine->vectorType(_engine->floatType(), 4);
564 break;
565
566 // dvec
567 case Parser::T_DVEC2:
568 _type = _engine->vectorType(_engine->doubleType(), 2);
569 break;
570
571 case Parser::T_DVEC3:
572 _type = _engine->vectorType(_engine->doubleType(), 3);
573 break;
574
575 case Parser::T_DVEC4:
576 _type = _engine->vectorType(_engine->doubleType(), 4);
577 break;
578
579 // mat2
580 case Parser::T_MAT2:
581 case Parser::T_MAT2X2:
582 _type = _engine->matrixType(_engine->floatType(), 2, 2);
583 break;
584
585 case Parser::T_MAT2X3:
586 _type = _engine->matrixType(_engine->floatType(), 2, 3);
587 break;
588
589 case Parser::T_MAT2X4:
590 _type = _engine->matrixType(_engine->floatType(), 2, 4);
591 break;
592
593 // mat3
594 case Parser::T_MAT3X2:
595 _type = _engine->matrixType(_engine->floatType(), 3, 2);
596 break;
597
598 case Parser::T_MAT3:
599 case Parser::T_MAT3X3:
600 _type = _engine->matrixType(_engine->floatType(), 3, 3);
601 break;
602
603 case Parser::T_MAT3X4:
604 _type = _engine->matrixType(_engine->floatType(), 3, 4);
605 break;
606
607 // mat4
608 case Parser::T_MAT4X2:
609 _type = _engine->matrixType(_engine->floatType(), 4, 2);
610 break;
611
612 case Parser::T_MAT4X3:
613 _type = _engine->matrixType(_engine->floatType(), 4, 3);
614 break;
615
616 case Parser::T_MAT4:
617 case Parser::T_MAT4X4:
618 _type = _engine->matrixType(_engine->floatType(), 4, 4);
619 break;
620
621
622 // dmat2
623 case Parser::T_DMAT2:
625 _type = _engine->matrixType(_engine->doubleType(), 2, 2);
626 break;
627
629 _type = _engine->matrixType(_engine->doubleType(), 2, 3);
630 break;
631
633 _type = _engine->matrixType(_engine->doubleType(), 2, 4);
634 break;
635
636 // dmat3
638 _type = _engine->matrixType(_engine->doubleType(), 3, 2);
639 break;
640
641 case Parser::T_DMAT3:
643 _type = _engine->matrixType(_engine->doubleType(), 3, 3);
644 break;
645
647 _type = _engine->matrixType(_engine->doubleType(), 3, 4);
648 break;
649
650 // dmat4
652 _type = _engine->matrixType(_engine->doubleType(), 4, 2);
653 break;
654
656 _type = _engine->matrixType(_engine->doubleType(), 4, 3);
657 break;
658
659 case Parser::T_DMAT4:
661 _type = _engine->matrixType(_engine->doubleType(), 4, 4);
662 break;
663
664 // samplers
705 _type = _engine->samplerType(ast->token);
706 break;
707
708 default:
709 _engine->error(ast->lineno, QString::fromLatin1("Unknown type `%1'").arg(QLatin1String(GLSLParserTable::spell[ast->token])));
710 }
711
712 return false;
713}
714
716{
717 if (ast->name) {
718 if (Symbol *s = _scope->lookup(*ast->name)) {
719 if (Struct *ty = s->asStruct()) {
720 _type = ty;
721 return false;
722 }
723 }
724 _engine->error(ast->lineno, QString::fromLatin1("Undefined type `%1'").arg(*ast->name));
725 }
726
727 return false;
728}
729
731{
732 const Type *elementType = type(ast->elementType);
733 Q_UNUSED(elementType)
735 _type = _engine->arrayType(elementType); // ### ignore the size for now
736 return false;
737}
738
740{
741 Struct *s = _engine->newStruct(_scope);
742 if (ast->name)
743 s->setName(*ast->name);
744 if (Scope *e = s->scope())
745 e->add(s);
746 Scope *previousScope = switchScope(s);
747 for (List<StructTypeAST::Field *> *it = ast->fields; it; it = it->next) {
748 StructTypeAST::Field *f = it->value;
749 if (Symbol *member = field(f))
750 s->add(member);
751 }
752 (void) switchScope(previousScope);
753 return false;
754}
755
757{
758 _type = type(ast->type);
759 for (List<LayoutQualifierAST *> *it = ast->layout_list; it; it = it->next) {
760 LayoutQualifierAST *q = it->value;
761 // q->name;
762 // q->number;
763 Q_UNUSED(q)
764 }
765 return false;
766}
767
768
769// declarations
771{
772 const Type *ty = type(ast->type);
773 Q_UNUSED(ty)
774 return false;
775}
776
778{
779 Q_UNUSED(ast)
780 Q_ASSERT(!"unreachable");
781 return false;
782}
783
785{
786 if (!ast->type)
787 return false;
788
789 const Type *ty = type(ast->type);
790 ExprResult initializer = expression(ast->initializer);
791 if (ast->name) {
792 QualifiedTypeAST *qtype = ast->type->asQualifiedType();
793 int qualifiers = 0;
794 if (qtype)
795 qualifiers = qtype->qualifiers;
796 Variable *var = _engine->newVariable(_scope, *ast->name, ty, qualifiers);
797 _scope->add(var);
798 }
799 return false;
800}
801
803{
804 const Type *ty = type(ast->type);
805 Q_UNUSED(ty)
806 return false;
807}
808
810{
811 declaration(ast->typeDecl);
812 declaration(ast->varDecl);
813 return false;
814}
815
817{
818 Q_UNUSED(ast)
819 return false;
820}
821
823{
824 for (List<DeclarationAST *> *it = ast->decls; it; it = it->next) {
825 DeclarationAST *decl = it->value;
826 declaration(decl);
827 }
828 return false;
829}
830
832{
833 Function *fun = _engine->newFunction(_scope);
834 if (ast->name)
835 fun->setName(*ast->name);
836
837 fun->setReturnType(type(ast->returnType));
838
839 for (List<ParameterDeclarationAST *> *it = ast->params; it; it = it->next) {
840 ParameterDeclarationAST *decl = it->value;
842 }
843
844 if (Scope *enclosingScope = fun->scope())
845 enclosingScope->add(fun);
846
847 Scope *previousScope = switchScope(fun);
848 statement(ast->body);
849 (void) switchScope(previousScope);
850 return false;
851}
852
static const char *const spell[]
virtual QualifiedTypeAST * asQualifiedType()
Definition glslast_p.h:248
@ Kind_BitwiseAnd
Definition glslast_p.h:150
@ Kind_GreaterThan
Definition glslast_p.h:145
@ Kind_LessThan
Definition glslast_p.h:143
@ Kind_GreaterEqual
Definition glslast_p.h:146
@ Kind_ArrayAccess
Definition glslast_p.h:154
@ Kind_ShiftLeft
Definition glslast_p.h:139
@ Kind_LessEqual
Definition glslast_p.h:144
@ Kind_BitwiseOr
Definition glslast_p.h:151
@ Kind_LogicalOr
Definition glslast_p.h:148
@ Kind_ShiftRight
Definition glslast_p.h:140
@ Kind_LogicalXor
Definition glslast_p.h:149
@ Kind_Multiply
Definition glslast_p.h:136
@ Kind_LogicalAnd
Definition glslast_p.h:147
@ Kind_BitwiseXor
Definition glslast_p.h:152
@ Kind_NotEqual
Definition glslast_p.h:142
ExpressionAST * size
Definition glslast_p.h:728
TypeAST * elementType
Definition glslast_p.h:727
ExpressionAST * left
Definition glslast_p.h:354
ExpressionAST * right
Definition glslast_p.h:355
List< StatementAST * > * statements
Definition glslast_p.h:513
ExpressionAST * condition
Definition glslast_p.h:563
StatementAST * body
Definition glslast_p.h:562
const UndefinedType * undefinedType()
const UIntType * uintType()
Struct * newStruct(Scope *scope=nullptr)
const MatrixType * matrixType(const Type *elementType, int columns, int rows)
const BoolType * boolType()
const ArrayType * arrayType(const Type *elementType)
const VoidType * voidType()
const IntType * intType()
const SamplerType * samplerType(int kind)
void error(int line, const QString &message)
const VectorType * vectorType(const Type *elementType, int dimension)
const DoubleType * doubleType()
Variable * newVariable(Scope *scope, const QString &name, const Type *type, int qualifiers=0)
Argument * newArgument(Function *function, const QString &name, const Type *type)
Block * newBlock(Scope *scope=nullptr)
const FloatType * floatType()
Function * newFunction(Scope *scope=nullptr)
StatementAST * body
Definition glslast_p.h:580
StatementAST * init
Definition glslast_p.h:577
ExpressionAST * condition
Definition glslast_p.h:578
ExpressionAST * increment
Definition glslast_p.h:579
List< ExpressionAST * > * arguments
Definition glslast_p.h:437
FunctionIdentifierAST * id
Definition glslast_p.h:436
List< ParameterDeclarationAST * > * params
Definition glslast_p.h:981
const Function * asFunctionType() const override
StatementAST * elseClause
Definition glslast_p.h:533
StatementAST * thenClause
Definition glslast_p.h:532
ExpressionAST * condition
Definition glslast_p.h:531
const IndexType * asIndexType() const override
List< DeclarationAST * > * decls
Definition glslast_p.h:960
const QString * value
Definition glslast_p.h:340
const MatrixType * asMatrixType() const override
const QString * name
Definition glslast_p.h:708
const OverloadSet * asOverloadSetType() const override
List< LayoutQualifierAST * > * layout_list
Definition glslast_p.h:832
ExpressionAST * expr
Definition glslast_p.h:605
virtual void add(Symbol *symbol)=0
Symbol * lookup(const QString &name) const
void parameterDeclaration(ParameterDeclarationAST *ast, Function *fun)
Symbol * field(StructTypeAST::Field *ast)
const Type * type(TypeAST *ast)
void declaration(DeclarationAST *ast)
void translationUnit(TranslationUnitAST *ast, Scope *globalScope, Engine *engine)
Scope * switchScope(Scope *scope)
void statement(StatementAST *ast)
Engine * switchEngine(Engine *engine)
~Semantic() override
ExprResult expression(ExpressionAST *ast, Scope *scope, Engine *engine)
bool visit(TranslationUnitAST *ast) override
ExprResult functionIdentifier(FunctionIdentifierAST *ast)
bool implicitCast(const Type *type, const Type *target) const
List< Field * > * fields
Definition glslast_p.h:772
const QString * name
Definition glslast_p.h:771
Struct * asStruct() override
StatementAST * body
Definition glslast_p.h:620
ExpressionAST * expr
Definition glslast_p.h:619
void setName(const QString &name)
ExpressionAST * first
Definition glslast_p.h:383
ExpressionAST * second
Definition glslast_p.h:384
ExpressionAST * third
Definition glslast_p.h:385
List< DeclarationAST * > * declarations
Definition glslast_p.h:303
VariableDeclarationAST * varDecl
Definition glslast_p.h:932
TypeDeclarationAST * typeDecl
Definition glslast_p.h:931
virtual const DoubleType * asDoubleType() const
Definition glsltype_p.h:38
virtual const VectorType * asVectorType() const
Definition glsltype_p.h:41
virtual const IntType * asIntType() const
Definition glsltype_p.h:35
virtual const Struct * asStructType() const
Definition glsltype_p.h:47
virtual const UIntType * asUIntType() const
Definition glsltype_p.h:36
virtual const FloatType * asFloatType() const
Definition glsltype_p.h:37
ExpressionAST * expr
Definition glslast_p.h:369
ExpressionAST * initializer
Definition glslast_p.h:901
const VectorType * asVectorType() const override
void accept(AST *ast)
StatementAST * body
Definition glslast_p.h:548
ExpressionAST * condition
Definition glslast_p.h:547
Definition qlist.h:74
qsizetype size() const noexcept
Definition qlist.h:386
bool isEmpty() const noexcept
Definition qlist.h:390
const_reference at(qsizetype i) const noexcept
Definition qlist.h:429
const T & constFirst() const noexcept
Definition qlist.h:630
void append(parameter_type t)
Definition qlist.h:441
\macro QT_RESTRICTED_CAST_FROM_ASCII
Definition qstring.h:127
static QString fromLatin1(QByteArrayView ba)
This is an overloaded member function, provided for convenience. It differs from the above function o...
Definition qstring.cpp:5710
QString arg(qlonglong a, int fieldwidth=0, int base=10, QChar fillChar=u' ') const
Definition qstring.cpp:8606
const QChar at(qsizetype i) const
Returns the character at the given index position in the string.
Definition qstring.h:1079
bool endsWith(const QString &s, Qt::CaseSensitivity cs=Qt::CaseSensitive) const
Returns true if the string ends with s; otherwise returns false.
Definition qstring.cpp:5350
bool contains(QChar c, Qt::CaseSensitivity cs=Qt::CaseSensitive) const
Definition qstring.h:1217
double e
QSet< QString >::iterator it
Definition glsl_p.h:22
Combined button and popup list for selecting options.
DBusConnection const char DBusError DBusBusType DBusError return DBusConnection DBusHandleMessageFunction void DBusFreeFunction return DBusConnection return DBusConnection return const char DBusError return DBusConnection DBusMessage dbus_uint32_t return DBusConnection dbus_bool_t DBusConnection DBusAddWatchFunction DBusRemoveWatchFunction DBusWatchToggledFunction void DBusFreeFunction return DBusConnection DBusDispatchStatusFunction void DBusFreeFunction DBusTimeout return DBusTimeout return DBusWatch return DBusWatch unsigned int return DBusError const DBusError return const DBusMessage return DBusMessage return DBusMessage return DBusMessage return DBusMessage return DBusMessage return DBusMessageIter int const void return DBusMessageIter DBusMessageIter return DBusMessageIter void DBusMessageIter void int return DBusMessage DBusMessageIter return DBusMessageIter return DBusMessageIter DBusMessageIter const char const char const char const char return DBusMessage return DBusMessage const char return DBusMessage dbus_bool_t return DBusMessage dbus_uint32_t return DBusMessage void
EGLOutputLayerEXT EGLint EGLAttrib value
[5]
GLenum GLuint GLintptr GLsizeiptr size
[1]
GLenum condition
GLboolean r
[2]
GLdouble GLdouble right
GLfloat GLfloat f
GLint left
GLenum type
GLenum target
GLuint name
GLint first
GLdouble GLdouble t
Definition qopenglext.h:243
GLdouble GLdouble GLdouble GLdouble q
Definition qopenglext.h:259
GLuint64EXT * result
[6]
GLdouble s
[6]
Definition qopenglext.h:235
GLenum GLenum variable
GLbyte ty
#define Q_ASSERT(cond)
Definition qrandom.cpp:47
SSL_CTX int(*) void arg)
#define Q_UNUSED(x)
QtConcurrent::task([]{ qDebug("Hello, world!");}).spawn(FutureResult void increment(QPromise< int > &promise, int i)
[10]
QObject::connect nullptr
QJSValue fun
[0]
QJSEngine engine
[0]
\inmodule QtCore \reentrant
Definition qchar.h:17