| OLD | NEW |
| 1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2013, the Dart project authors. Please see the AUTHORS file |
| 2 // for details. All rights reserved. Use of this source code is governed by a | 2 // for details. All rights reserved. Use of this source code is governed by a |
| 3 // BSD-style license that can be found in the LICENSE file. | 3 // BSD-style license that can be found in the LICENSE file. |
| 4 | 4 |
| 5 #include "vm/intermediate_language.h" | 5 #include "vm/intermediate_language.h" |
| 6 | 6 |
| 7 #include "vm/bigint_operations.h" | 7 #include "vm/bigint_operations.h" |
| 8 #include "vm/bit_vector.h" | 8 #include "vm/bit_vector.h" |
| 9 #include "vm/cpu.h" | 9 #include "vm/cpu.h" |
| 10 #include "vm/dart_entry.h" | 10 #include "vm/dart_entry.h" |
| (...skipping 66 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 77 } | 77 } |
| 78 return AttributesEqual(other); | 78 return AttributesEqual(other); |
| 79 } | 79 } |
| 80 | 80 |
| 81 | 81 |
| 82 bool Value::Equals(Value* other) const { | 82 bool Value::Equals(Value* other) const { |
| 83 return definition() == other->definition(); | 83 return definition() == other->definition(); |
| 84 } | 84 } |
| 85 | 85 |
| 86 | 86 |
| 87 static int LowestFirst(const intptr_t* a, const intptr_t* b) { |
| 88 return *a - *b; |
| 89 } |
| 90 |
| 91 |
| 87 CheckClassInstr::CheckClassInstr(Value* value, | 92 CheckClassInstr::CheckClassInstr(Value* value, |
| 88 intptr_t deopt_id, | 93 intptr_t deopt_id, |
| 89 const ICData& unary_checks) | 94 const ICData& unary_checks) |
| 90 : unary_checks_(unary_checks), licm_hoisted_(false) { | 95 : unary_checks_(unary_checks), |
| 96 cids_(unary_checks.NumberOfChecks()), |
| 97 licm_hoisted_(false) { |
| 91 ASSERT(unary_checks.IsZoneHandle()); | 98 ASSERT(unary_checks.IsZoneHandle()); |
| 92 // Expected useful check data. | 99 // Expected useful check data. |
| 93 ASSERT(!unary_checks_.IsNull()); | 100 ASSERT(!unary_checks_.IsNull()); |
| 94 ASSERT(unary_checks_.NumberOfChecks() > 0); | 101 ASSERT(unary_checks_.NumberOfChecks() > 0); |
| 95 ASSERT(unary_checks_.num_args_tested() == 1); | 102 ASSERT(unary_checks_.num_args_tested() == 1); |
| 96 SetInputAt(0, value); | 103 SetInputAt(0, value); |
| 97 deopt_id_ = deopt_id; | 104 deopt_id_ = deopt_id; |
| 98 // Otherwise use CheckSmiInstr. | 105 // Otherwise use CheckSmiInstr. |
| 99 ASSERT((unary_checks_.NumberOfChecks() != 1) || | 106 ASSERT((unary_checks_.NumberOfChecks() != 1) || |
| 100 (unary_checks_.GetReceiverClassIdAt(0) != kSmiCid)); | 107 (unary_checks_.GetReceiverClassIdAt(0) != kSmiCid)); |
| 108 for (intptr_t i = 0; i < unary_checks.NumberOfChecks(); ++i) { |
| 109 cids_.Add(unary_checks.GetReceiverClassIdAt(i)); |
| 110 } |
| 111 cids_.Sort(LowestFirst); |
| 101 } | 112 } |
| 102 | 113 |
| 103 | 114 |
| 104 bool CheckClassInstr::AttributesEqual(Instruction* other) const { | 115 bool CheckClassInstr::AttributesEqual(Instruction* other) const { |
| 105 CheckClassInstr* other_check = other->AsCheckClass(); | 116 CheckClassInstr* other_check = other->AsCheckClass(); |
| 106 ASSERT(other_check != NULL); | 117 ASSERT(other_check != NULL); |
| 107 if (unary_checks().NumberOfChecks() != | 118 if (unary_checks().NumberOfChecks() != |
| 108 other_check->unary_checks().NumberOfChecks()) { | 119 other_check->unary_checks().NumberOfChecks()) { |
| 109 return false; | 120 return false; |
| 110 } | 121 } |
| (...skipping 22 matching lines...) Expand all Loading... |
| 133 return false; | 144 return false; |
| 134 } | 145 } |
| 135 CompileType* in_type = value()->Type(); | 146 CompileType* in_type = value()->Type(); |
| 136 const intptr_t cid = unary_checks().GetCidAt(0); | 147 const intptr_t cid = unary_checks().GetCidAt(0); |
| 137 // Performance check: use CheckSmiInstr instead. | 148 // Performance check: use CheckSmiInstr instead. |
| 138 ASSERT(cid != kSmiCid); | 149 ASSERT(cid != kSmiCid); |
| 139 return in_type->is_nullable() && (in_type->ToNullableCid() == cid); | 150 return in_type->is_nullable() && (in_type->ToNullableCid() == cid); |
| 140 } | 151 } |
| 141 | 152 |
| 142 | 153 |
| 154 bool CheckClassInstr::IsDenseSwitch() const { |
| 155 return unary_checks().GetReceiverClassIdAt(0) != kSmiCid |
| 156 && cids_.length() > 2 |
| 157 && cids_[cids_.length() - 1] - cids_[0] < kBitsPerWord; |
| 158 } |
| 159 |
| 160 |
| 143 bool LoadFieldInstr::IsUnboxedLoad() const { | 161 bool LoadFieldInstr::IsUnboxedLoad() const { |
| 144 return FLAG_unbox_numeric_fields | 162 return FLAG_unbox_numeric_fields |
| 145 && (field() != NULL) | 163 && (field() != NULL) |
| 146 && field()->IsUnboxedField(); | 164 && field()->IsUnboxedField(); |
| 147 } | 165 } |
| 148 | 166 |
| 149 | 167 |
| 150 bool LoadFieldInstr::IsPotentialUnboxedLoad() const { | 168 bool LoadFieldInstr::IsPotentialUnboxedLoad() const { |
| 151 return FLAG_unbox_numeric_fields | 169 return FLAG_unbox_numeric_fields |
| 152 && (field() != NULL) | 170 && (field() != NULL) |
| (...skipping 3075 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 3228 case Token::kTRUNCDIV: return 0; | 3246 case Token::kTRUNCDIV: return 0; |
| 3229 case Token::kMOD: return 1; | 3247 case Token::kMOD: return 1; |
| 3230 default: UNIMPLEMENTED(); return -1; | 3248 default: UNIMPLEMENTED(); return -1; |
| 3231 } | 3249 } |
| 3232 } | 3250 } |
| 3233 | 3251 |
| 3234 | 3252 |
| 3235 #undef __ | 3253 #undef __ |
| 3236 | 3254 |
| 3237 } // namespace dart | 3255 } // namespace dart |
| OLD | NEW |