| OLD | NEW |
| 1 // Copyright (c) 2012, the Dart project authors. Please see the AUTHORS file | 1 // Copyright (c) 2012, 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/object.h" | 5 #include "vm/object.h" |
| 6 | 6 |
| 7 #include "include/dart_api.h" | 7 #include "include/dart_api.h" |
| 8 #include "platform/assert.h" | 8 #include "platform/assert.h" |
| 9 #include "vm/assembler.h" | 9 #include "vm/assembler.h" |
| 10 #include "vm/cpu.h" | 10 #include "vm/cpu.h" |
| (...skipping 13006 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 13017 result.AddReceiverCheck(class_id, | 13017 result.AddReceiverCheck(class_id, |
| 13018 Function::Handle(GetTargetAt(i)), | 13018 Function::Handle(GetTargetAt(i)), |
| 13019 count); | 13019 count); |
| 13020 } | 13020 } |
| 13021 } | 13021 } |
| 13022 | 13022 |
| 13023 return result.raw(); | 13023 return result.raw(); |
| 13024 } | 13024 } |
| 13025 | 13025 |
| 13026 | 13026 |
| 13027 // (cid, count) tuple used to sort ICData by count. |
| 13028 struct CidCount { |
| 13029 CidCount(intptr_t cid_, intptr_t count_, Function* f_) |
| 13030 : cid(cid_), count(count_), function(f_) {} |
| 13031 |
| 13032 static int HighestCountFirst(const CidCount* a, const CidCount* b); |
| 13033 |
| 13034 intptr_t cid; |
| 13035 intptr_t count; |
| 13036 Function* function; |
| 13037 }; |
| 13038 |
| 13039 |
| 13040 int CidCount::HighestCountFirst(const CidCount* a, const CidCount* b) { |
| 13041 if (a->count > b->count) { |
| 13042 return -1; |
| 13043 } |
| 13044 return (a->count < b->count) ? 1 : 0; |
| 13045 } |
| 13046 |
| 13047 |
| 13048 RawICData* ICData::AsUnaryClassChecksSortedByCount() const { |
| 13049 ASSERT(!IsNull()); |
| 13050 const intptr_t kNumArgsTested = 1; |
| 13051 const intptr_t len = NumberOfChecks(); |
| 13052 if (len <= 1) { |
| 13053 // No sorting needed. |
| 13054 return AsUnaryClassChecks(); |
| 13055 } |
| 13056 GrowableArray<CidCount> aggregate; |
| 13057 for (intptr_t i = 0; i < len; i++) { |
| 13058 const intptr_t class_id = GetClassIdAt(i, 0); |
| 13059 const intptr_t count = GetCountAt(i); |
| 13060 if (count == 0) { |
| 13061 continue; |
| 13062 } |
| 13063 bool found = false; |
| 13064 for (intptr_t r = 0; r < aggregate.length(); r++) { |
| 13065 if (aggregate[r].cid == class_id) { |
| 13066 aggregate[r].count += count; |
| 13067 found = true; |
| 13068 break; |
| 13069 } |
| 13070 } |
| 13071 if (!found) { |
| 13072 aggregate.Add(CidCount(class_id, count, |
| 13073 &Function::ZoneHandle(GetTargetAt(i)))); |
| 13074 } |
| 13075 } |
| 13076 aggregate.Sort(CidCount::HighestCountFirst); |
| 13077 |
| 13078 ICData& result = ICData::Handle(ICData::NewFrom(*this, kNumArgsTested)); |
| 13079 ASSERT(result.NumberOfChecks() == 0); |
| 13080 // Room for all entries and the sentinel. |
| 13081 const intptr_t data_len = |
| 13082 result.TestEntryLength() * (aggregate.length() + 1); |
| 13083 const Array& data = Array::Handle(Array::New(data_len, Heap::kOld)); |
| 13084 result.set_ic_data_array(data); |
| 13085 ASSERT(result.NumberOfChecks() == aggregate.length()); |
| 13086 |
| 13087 intptr_t pos = 0; |
| 13088 for (intptr_t i = 0; i < aggregate.length(); i++) { |
| 13089 data.SetAt(pos + 0, Smi::Handle(Smi::New(aggregate[i].cid))); |
| 13090 data.SetAt(pos + TargetIndexFor(1), *aggregate[i].function); |
| 13091 data.SetAt(pos + CountIndexFor(1), |
| 13092 Smi::Handle(Smi::New(aggregate[i].count))); |
| 13093 |
| 13094 pos += result.TestEntryLength(); |
| 13095 } |
| 13096 WriteSentinel(data, result.TestEntryLength()); |
| 13097 result.set_ic_data_array(data); |
| 13098 return result.raw(); |
| 13099 } |
| 13100 |
| 13101 |
| 13027 bool ICData::AllTargetsHaveSameOwner(intptr_t owner_cid) const { | 13102 bool ICData::AllTargetsHaveSameOwner(intptr_t owner_cid) const { |
| 13028 if (NumberOfChecks() == 0) return false; | 13103 if (NumberOfChecks() == 0) return false; |
| 13029 Class& cls = Class::Handle(); | 13104 Class& cls = Class::Handle(); |
| 13030 const intptr_t len = NumberOfChecks(); | 13105 const intptr_t len = NumberOfChecks(); |
| 13031 for (intptr_t i = 0; i < len; i++) { | 13106 for (intptr_t i = 0; i < len; i++) { |
| 13032 if (IsUsedAt(i)) { | 13107 if (IsUsedAt(i)) { |
| 13033 cls = Function::Handle(GetTargetAt(i)).Owner(); | 13108 cls = Function::Handle(GetTargetAt(i)).Owner(); |
| 13034 if (cls.id() != owner_cid) { | 13109 if (cls.id() != owner_cid) { |
| 13035 return false; | 13110 return false; |
| 13036 } | 13111 } |
| (...skipping 9285 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 22322 return UserTag::null(); | 22397 return UserTag::null(); |
| 22323 } | 22398 } |
| 22324 | 22399 |
| 22325 | 22400 |
| 22326 const char* UserTag::ToCString() const { | 22401 const char* UserTag::ToCString() const { |
| 22327 const String& tag_label = String::Handle(label()); | 22402 const String& tag_label = String::Handle(label()); |
| 22328 return tag_label.ToCString(); | 22403 return tag_label.ToCString(); |
| 22329 } | 22404 } |
| 22330 | 22405 |
| 22331 } // namespace dart | 22406 } // namespace dart |
| OLD | NEW |