Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 /* | 1 /* |
| 2 * Copyright 2016 Google Inc. | 2 * Copyright 2016 Google Inc. |
| 3 * | 3 * |
| 4 * Use of this source code is governed by a BSD-style license that can be | 4 * Use of this source code is governed by a BSD-style license that can be |
| 5 * found in the LICENSE file. | 5 * found in the LICENSE file. |
| 6 */ | 6 */ |
| 7 | 7 |
| 8 #include "SkSLIRGenerator.h" | 8 #include "SkSLIRGenerator.h" |
| 9 | 9 |
| 10 #include "limits.h" | 10 #include "limits.h" |
| (...skipping 164 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 175 } | 175 } |
| 176 type = new Type(name, Type::kArray_Kind, *type, (int) count); | 176 type = new Type(name, Type::kArray_Kind, *type, (int) count); |
| 177 fSymbolTable->takeOwnership((Type*) type); | 177 fSymbolTable->takeOwnership((Type*) type); |
| 178 currentVarSizes.push_back(std::move(size)); | 178 currentVarSizes.push_back(std::move(size)); |
| 179 } else { | 179 } else { |
| 180 type = new Type(type->fName + "[]", Type::kArray_Kind, *type, -1 ); | 180 type = new Type(type->fName + "[]", Type::kArray_Kind, *type, -1 ); |
| 181 fSymbolTable->takeOwnership((Type*) type); | 181 fSymbolTable->takeOwnership((Type*) type); |
| 182 currentVarSizes.push_back(nullptr); | 182 currentVarSizes.push_back(nullptr); |
| 183 } | 183 } |
| 184 } | 184 } |
| 185 sizes.push_back(std::move(currentVarSizes)); | |
| 186 auto var = std::unique_ptr<Variable>(new Variable(decl.fPosition, modifi ers, decl.fNames[i], | 185 auto var = std::unique_ptr<Variable>(new Variable(decl.fPosition, modifi ers, decl.fNames[i], |
| 187 *type, storage)); | 186 *type, storage)); |
| 188 std::unique_ptr<Expression> value; | 187 std::unique_ptr<Expression> value; |
| 189 if (decl.fValues[i]) { | 188 if (decl.fValues[i]) { |
| 190 value = this->convertExpression(*decl.fValues[i]); | 189 value = this->convertExpression(*decl.fValues[i]); |
| 191 if (!value) { | 190 if (!value) { |
| 192 return nullptr; | 191 return nullptr; |
| 193 } | 192 } |
| 194 value = this->coerce(std::move(value), *type); | 193 value = this->coerce(std::move(value), *type); |
| 195 } | 194 } |
| 196 variables.push_back(var.get()); | 195 if ("gl_FragCoord" == decl.fNames[i] && (*fSymbolTable)[decl.fNames[i]]) { |
| 197 fSymbolTable->add(decl.fNames[i], std::move(var)); | 196 // already defined, just update the modifiers |
| 198 values.push_back(std::move(value)); | 197 Variable* old = (Variable*) (*fSymbolTable)[decl.fNames[i]]; |
| 198 old->fModifiers = var->fModifiers; | |
| 199 } else { | |
| 200 variables.push_back(var.get()); | |
| 201 fSymbolTable->add(decl.fNames[i], std::move(var)); | |
| 202 values.push_back(std::move(value)); | |
| 203 sizes.push_back(std::move(currentVarSizes)); | |
| 204 } | |
| 199 } | 205 } |
| 200 return std::unique_ptr<VarDeclaration>(new VarDeclaration(decl.fPosition, st d::move(variables), | 206 return std::unique_ptr<VarDeclaration>(new VarDeclaration(decl.fPosition, |
| 201 std::move(sizes), std::move(values))); | 207 baseType, |
| 208 std::move(variable s), | |
| 209 std::move(sizes), | |
| 210 std::move(values)) ); | |
| 202 } | 211 } |
| 203 | 212 |
| 204 std::unique_ptr<Statement> IRGenerator::convertIf(const ASTIfStatement& s) { | 213 std::unique_ptr<Statement> IRGenerator::convertIf(const ASTIfStatement& s) { |
| 205 std::unique_ptr<Expression> test = this->coerce(this->convertExpression(*s.f Test), | 214 std::unique_ptr<Expression> test = this->coerce(this->convertExpression(*s.f Test), |
| 206 *fContext.fBool_Type); | 215 *fContext.fBool_Type); |
| 207 if (!test) { | 216 if (!test) { |
| 208 return nullptr; | 217 return nullptr; |
| 209 } | 218 } |
| 210 std::unique_ptr<Statement> ifTrue = this->convertStatement(*s.fIfTrue); | 219 std::unique_ptr<Statement> ifTrue = this->convertStatement(*s.fIfTrue); |
| 211 if (!ifTrue) { | 220 if (!ifTrue) { |
| (...skipping 354 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 566 } | 575 } |
| 567 case Symbol::kVariable_Kind: { | 576 case Symbol::kVariable_Kind: { |
| 568 const Variable* var = (const Variable*) result; | 577 const Variable* var = (const Variable*) result; |
| 569 this->markReadFrom(*var); | 578 this->markReadFrom(*var); |
| 570 return std::unique_ptr<VariableReference>(new VariableReference(iden tifier.fPosition, | 579 return std::unique_ptr<VariableReference>(new VariableReference(iden tifier.fPosition, |
| 571 *var )); | 580 *var )); |
| 572 } | 581 } |
| 573 case Symbol::kField_Kind: { | 582 case Symbol::kField_Kind: { |
| 574 const Field* field = (const Field*) result; | 583 const Field* field = (const Field*) result; |
| 575 VariableReference* base = new VariableReference(identifier.fPosition , field->fOwner); | 584 VariableReference* base = new VariableReference(identifier.fPosition , field->fOwner); |
| 576 return std::unique_ptr<Expression>(new FieldAccess(std::unique_ptr<E xpression>(base), | 585 return std::unique_ptr<Expression>(new FieldAccess( |
| 577 field->fFieldInde x)); | 586 std::unique_ptr<Expression>(ba se), |
| 587 field->fFieldIndex, | |
| 588 FieldAccess::kAnonymousInterfa ceBlock_OwnerKind)); | |
| 578 } | 589 } |
| 579 case Symbol::kType_Kind: { | 590 case Symbol::kType_Kind: { |
| 580 const Type* t = (const Type*) result; | 591 const Type* t = (const Type*) result; |
| 581 return std::unique_ptr<TypeReference>(new TypeReference(fContext, id entifier.fPosition, | 592 return std::unique_ptr<TypeReference>(new TypeReference(fContext, id entifier.fPosition, |
| 582 *t)); | 593 *t)); |
| 583 } | 594 } |
| 584 default: | 595 default: |
| 585 ABORT("unsupported symbol type %d\n", result->fKind); | 596 ABORT("unsupported symbol type %d\n", result->fKind); |
| 586 } | 597 } |
| 587 | 598 |
| (...skipping 21 matching lines...) Expand all Loading... | |
| 609 args.push_back(std::move(expr)); | 620 args.push_back(std::move(expr)); |
| 610 ASTIdentifier id(Position(), type.description()); | 621 ASTIdentifier id(Position(), type.description()); |
| 611 std::unique_ptr<Expression> ctor = this->convertIdentifier(id); | 622 std::unique_ptr<Expression> ctor = this->convertIdentifier(id); |
| 612 ASSERT(ctor); | 623 ASSERT(ctor); |
| 613 return this->call(Position(), std::move(ctor), std::move(args)); | 624 return this->call(Position(), std::move(ctor), std::move(args)); |
| 614 } | 625 } |
| 615 ABORT("cannot coerce %s to %s", expr->fType.description().c_str(), | 626 ABORT("cannot coerce %s to %s", expr->fType.description().c_str(), |
| 616 type.description().c_str()); | 627 type.description().c_str()); |
| 617 } | 628 } |
| 618 | 629 |
| 630 static bool is_matrix_multiply(const Type& left, const Type& right) { | |
| 631 if (left.kind() == Type::kMatrix_Kind) { | |
| 632 return right.kind() == Type::kMatrix_Kind || right.kind() == Type::kVect or_Kind; | |
| 633 } | |
| 634 return left.kind() == Type::kVector_Kind && right.kind() == Type::kMatrix_Ki nd; | |
| 635 } | |
| 619 /** | 636 /** |
| 620 * Determines the operand and result types of a binary expression. Returns true if the expression is | 637 * Determines the operand and result types of a binary expression. Returns true if the expression is |
| 621 * legal, false otherwise. If false, the values of the out parameters are undefi ned. | 638 * legal, false otherwise. If false, the values of the out parameters are undefi ned. |
| 622 */ | 639 */ |
| 623 static bool determine_binary_type(const Context& context, | 640 static bool determine_binary_type(const Context& context, |
| 624 Token::Kind op, | 641 Token::Kind op, |
| 625 const Type& left, | 642 const Type& left, |
| 626 const Type& right, | 643 const Type& right, |
| 627 const Type** outLeftType, | 644 const Type** outLeftType, |
| 628 const Type** outRightType, | 645 const Type** outRightType, |
| (...skipping 15 matching lines...) Expand all Loading... | |
| 644 case Token::LOGICALOREQ: // fall through | 661 case Token::LOGICALOREQ: // fall through |
| 645 case Token::LOGICALANDEQ: // fall through | 662 case Token::LOGICALANDEQ: // fall through |
| 646 case Token::LOGICALXOREQ: | 663 case Token::LOGICALXOREQ: |
| 647 *outLeftType = context.fBool_Type.get(); | 664 *outLeftType = context.fBool_Type.get(); |
| 648 *outRightType = context.fBool_Type.get(); | 665 *outRightType = context.fBool_Type.get(); |
| 649 *outResultType = context.fBool_Type.get(); | 666 *outResultType = context.fBool_Type.get(); |
| 650 return left.canCoerceTo(*context.fBool_Type) && | 667 return left.canCoerceTo(*context.fBool_Type) && |
| 651 right.canCoerceTo(*context.fBool_Type); | 668 right.canCoerceTo(*context.fBool_Type); |
| 652 case Token::STAR: // fall through | 669 case Token::STAR: // fall through |
| 653 case Token::STAREQ: | 670 case Token::STAREQ: |
| 654 // FIXME need to handle non-square matrices | 671 if (is_matrix_multiply(left, right)) { |
| 655 if (left.kind() == Type::kMatrix_Kind && right.kind() == Type::kVect or_Kind) { | 672 // determine final component type |
| 656 *outLeftType = &left; | 673 if (determine_binary_type(context, Token::STAR, left.componentTy pe(), |
| 657 *outRightType = &right; | 674 right.componentType(), outLeftType, ou tRightType, |
| 658 *outResultType = &right; | 675 outResultType, false)) { |
| 659 return left.rows() == right.columns(); | 676 *outLeftType = &(*outResultType)->toCompound(context, left.c olumns(), |
| 660 } | 677 left.rows());; |
| 661 if (left.kind() == Type::kVector_Kind && right.kind() == Type::kMatr ix_Kind) { | 678 *outRightType = &(*outResultType)->toCompound(context, right .columns(), |
| 662 *outLeftType = &left; | 679 right.rows()); ; |
| 663 *outRightType = &right; | 680 int leftColumns = left.columns(); |
| 664 *outResultType = &left; | 681 int leftRows = left.rows(); |
| 665 return left.columns() == right.columns(); | 682 int rightColumns; |
| 683 int rightRows; | |
| 684 if (right.kind() == Type::kVector_Kind) { | |
| 685 rightColumns = right.rows(); | |
|
dogben
2016/08/02 18:08:15
nit: Maybe add comment: "Vector on right is implic
ethannicholas
2016/08/02 20:43:06
Done.
| |
| 686 rightRows = right.columns(); | |
| 687 ASSERT(rightColumns == 1); | |
| 688 } else { | |
| 689 rightColumns = right.columns(); | |
| 690 rightRows = right.rows(); | |
| 691 } | |
| 692 if (rightColumns > 1) { | |
|
dogben
2016/08/02 18:08:15
nit: Maybe add comment: "Single-column result is i
ethannicholas
2016/08/02 20:43:06
Done.
| |
| 693 *outResultType = &(*outResultType)->toCompound(context, rightColumns, | |
| 694 leftRows) ; | |
| 695 } else { | |
| 696 *outResultType = &(*outResultType)->toCompound(context, leftRows, | |
| 697 rightColu mns); | |
| 698 } | |
| 699 return leftColumns == rightRows; | |
| 700 } else { | |
| 701 return false; | |
| 702 } | |
| 666 } | 703 } |
| 667 // fall through | 704 // fall through |
| 668 default: | 705 default: |
| 669 isLogical = false; | 706 isLogical = false; |
| 670 } | 707 } |
| 671 // FIXME: need to disallow illegal operations like vec3 > vec3. Also do not currently have | 708 // FIXME: need to disallow illegal operations like vec3 > vec3. Also do not currently have |
| 672 // full support for numbers other than float. | 709 // full support for numbers other than float. |
| 673 if (left == right) { | 710 if (left == right) { |
| 674 *outLeftType = &left; | 711 *outLeftType = &left; |
| 675 *outRightType = &left; | 712 *outRightType = &left; |
| (...skipping 542 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
| 1218 case Expression::kIndex_Kind: | 1255 case Expression::kIndex_Kind: |
| 1219 this->markWrittenTo(*((IndexExpression&) expr).fBase); | 1256 this->markWrittenTo(*((IndexExpression&) expr).fBase); |
| 1220 break; | 1257 break; |
| 1221 default: | 1258 default: |
| 1222 fErrors.error(expr.fPosition, "cannot assign to '" + expr.descriptio n() + "'"); | 1259 fErrors.error(expr.fPosition, "cannot assign to '" + expr.descriptio n() + "'"); |
| 1223 break; | 1260 break; |
| 1224 } | 1261 } |
| 1225 } | 1262 } |
| 1226 | 1263 |
| 1227 } | 1264 } |
| OLD | NEW |