Chromium Code Reviews| Index: runtime/vm/ast.cc |
| =================================================================== |
| --- runtime/vm/ast.cc (revision 24703) |
| +++ runtime/vm/ast.cc (working copy) |
| @@ -110,6 +110,11 @@ |
| } |
| +bool LiteralNode::IsPotentiallyConst() const { |
| + return true; |
| +} |
| + |
| + |
| // TODO(srdjan): Add code for logical negation. |
| AstNode* LiteralNode::ApplyUnaryOp(Token::Kind unary_op_kind) { |
| if (unary_op_kind == Token::kNEGATE) { |
| @@ -145,6 +150,24 @@ |
| } |
| +bool ComparisonNode::IsPotentiallyConst() const { |
| + switch (kind_) { |
| + case Token::kLT: |
| + case Token::kGT: |
| + case Token::kLTE: |
| + case Token::kGTE: |
| + case Token::kEQ: |
| + case Token::kNE: |
| + case Token::kEQ_STRICT: |
| + case Token::kNE_STRICT: |
| + return this->left()->IsPotentiallyConst() && |
| + this->right()->IsPotentiallyConst(); |
| + default: |
| + return false; |
| + } |
| +} |
| + |
| + |
| const Instance* ComparisonNode::EvalConstExpr() const { |
| const Instance* left_val = this->left()->EvalConstExpr(); |
| if (left_val == NULL) { |
| @@ -216,6 +239,30 @@ |
| } |
| +bool BinaryOpNode::IsPotentiallyConst() const { |
| + switch (kind_) { |
| + case Token::kADD: |
| + case Token::kSUB: |
| + case Token::kMUL: |
| + case Token::kDIV: |
| + case Token::kMOD: |
| + case Token::kTRUNCDIV: |
| + case Token::kBIT_OR: |
| + case Token::kBIT_XOR: |
| + case Token::kBIT_AND: |
| + case Token::kSHL: |
| + case Token::kSHR: |
| + case Token::kOR: |
| + case Token::kAND: |
| + return this->left()->IsPotentiallyConst() && |
| + this->right()->IsPotentiallyConst(); |
| + default: |
| + UNREACHABLE(); |
| + return false; |
| + } |
| +} |
| + |
| + |
| const Instance* BinaryOpNode::EvalConstExpr() const { |
| const Instance* left_val = this->left()->EvalConstExpr(); |
| if (left_val == NULL) { |
| @@ -294,6 +341,11 @@ |
| } |
| +bool UnaryOpNode::IsPotentiallyConst() const { |
| + return true; |
|
Ivan Posva
2013/07/03 20:23:42
Shouldn't the operand also be potentially const?
hausner
2013/07/03 21:20:54
Actually, yes. Fixed.
|
| +} |
| + |
| + |
| const Instance* UnaryOpNode::EvalConstExpr() const { |
| const Instance* val = this->operand()->EvalConstExpr(); |
| if (val == NULL) { |
| @@ -313,6 +365,14 @@ |
| } |
| +bool ClosureNode::IsPotentiallyConst() const { |
| + if (function().IsImplicitStaticClosureFunction()) { |
| + return true; |
| + } |
| + return false; |
| +} |
| + |
| + |
| const Instance* ClosureNode::EvalConstExpr() const { |
| if (function().IsImplicitStaticClosureFunction()) { |
| // Return a value that represents an instance. Only the type is relevant. |
| @@ -347,6 +407,11 @@ |
| } |
| +bool LoadLocalNode::IsPotentiallyConst() const { |
| + return true; |
|
Ivan Posva
2013/07/03 20:23:42
Really? Thanks for the offline explanation, it wou
hausner
2013/07/03 21:20:54
Added comment and checked that the local variable/
|
| +} |
| + |
| + |
| const Instance* LoadLocalNode::EvalConstExpr() const { |
| if (local().IsConst()) { |
| return local().ConstValue(); |
| @@ -447,6 +512,18 @@ |
| } |
| +bool StaticGetterNode::IsPotentiallyConst() const { |
| + const String& getter_name = |
| + String::Handle(Field::GetterName(this->field_name())); |
| + const Function& getter_func = |
| + Function::Handle(this->cls().LookupStaticFunction(getter_name)); |
| + if (getter_func.IsNull() || !getter_func.is_const()) { |
| + return false; |
| + } |
| + return true; |
| +} |
| + |
| + |
| const Instance* StaticGetterNode::EvalConstExpr() const { |
| const String& getter_name = |
| String::Handle(Field::GetterName(this->field_name())); |