| 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/coverage.h" | 5 #include "vm/coverage.h" |
| 6 | 6 |
| 7 #include "include/dart_api.h" | 7 #include "include/dart_api.h" |
| 8 | 8 |
| 9 #include "vm/compiler.h" | 9 #include "vm/compiler.h" |
| 10 #include "vm/isolate.h" | 10 #include "vm/isolate.h" |
| (...skipping 54 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 65 } | 65 } |
| 66 if (function.IsNonImplicitClosureFunction() && | 66 if (function.IsNonImplicitClosureFunction() && |
| 67 (function.context_scope() == ContextScope::null())) { | 67 (function.context_scope() == ContextScope::null())) { |
| 68 // TODO(iposva): This can arise if we attempt to compile an inner function | 68 // TODO(iposva): This can arise if we attempt to compile an inner function |
| 69 // before we have compiled its enclosing function or if the enclosing | 69 // before we have compiled its enclosing function or if the enclosing |
| 70 // function failed to compile. | 70 // function failed to compile. |
| 71 return; | 71 return; |
| 72 } | 72 } |
| 73 Thread* thread = Thread::Current(); | 73 Thread* thread = Thread::Current(); |
| 74 Zone* zone = thread->zone(); | 74 Zone* zone = thread->zone(); |
| 75 Isolate* isolate = thread->isolate(); | |
| 76 // Make sure we have the unoptimized code for this function available. | 75 // Make sure we have the unoptimized code for this function available. |
| 77 if (Compiler::EnsureUnoptimizedCode(thread, function) != Error::null()) { | 76 if (Compiler::EnsureUnoptimizedCode(thread, function) != Error::null()) { |
| 78 // Ignore the error and this function entirely. | 77 // Ignore the error and this function entirely. |
| 79 return; | 78 return; |
| 80 } | 79 } |
| 81 const Code& code = Code::Handle(zone, function.unoptimized_code()); | 80 const Code& code = Code::Handle(zone, function.unoptimized_code()); |
| 82 ASSERT(!code.IsNull()); | 81 ASSERT(!code.IsNull()); |
| 83 | 82 |
| 84 // Print the hit counts for all IC datas. | 83 // Print the hit counts for all IC datas. |
| 85 ZoneGrowableArray<const ICData*>* ic_data_array = | 84 ZoneGrowableArray<const ICData*>* ic_data_array = |
| 86 new(zone) ZoneGrowableArray<const ICData*>(); | 85 new(zone) ZoneGrowableArray<const ICData*>(); |
| 87 function.RestoreICDataMap(ic_data_array); | 86 function.RestoreICDataMap(ic_data_array); |
| 88 const PcDescriptors& descriptors = PcDescriptors::Handle( | 87 const PcDescriptors& descriptors = PcDescriptors::Handle( |
| 89 zone, code.pc_descriptors()); | 88 zone, code.pc_descriptors()); |
| 90 | 89 |
| 91 const intptr_t begin_pos = function.token_pos(); | 90 const intptr_t begin_pos = function.token_pos(); |
| 92 const intptr_t end_pos = function.end_token_pos(); | 91 const intptr_t end_pos = function.end_token_pos(); |
| 93 intptr_t last_line = -1; | 92 intptr_t last_line = -1; |
| 94 intptr_t last_count = 0; | 93 intptr_t last_count = 0; |
| 95 // Only IC based calls have counting. | 94 // Only IC based calls have counting. |
| 96 PcDescriptors::Iterator iter(descriptors, | 95 PcDescriptors::Iterator iter(descriptors, |
| 97 RawPcDescriptors::kIcCall | RawPcDescriptors::kUnoptStaticCall); | 96 RawPcDescriptors::kIcCall | RawPcDescriptors::kUnoptStaticCall); |
| 98 while (iter.MoveNext()) { | 97 while (iter.MoveNext()) { |
| 99 HANDLESCOPE(isolate); | 98 HANDLESCOPE(thread); |
| 100 const ICData* ic_data = (*ic_data_array)[iter.DeoptId()]; | 99 const ICData* ic_data = (*ic_data_array)[iter.DeoptId()]; |
| 101 if (!ic_data->IsNull()) { | 100 if (!ic_data->IsNull()) { |
| 102 const intptr_t token_pos = iter.TokenPos(); | 101 const intptr_t token_pos = iter.TokenPos(); |
| 103 // Filter out descriptors that do not map to tokens in the source code. | 102 // Filter out descriptors that do not map to tokens in the source code. |
| 104 if ((token_pos < begin_pos) || (token_pos > end_pos)) { | 103 if ((token_pos < begin_pos) || (token_pos > end_pos)) { |
| 105 continue; | 104 continue; |
| 106 } | 105 } |
| 107 intptr_t line = pos_to_line[token_pos]; | 106 intptr_t line = pos_to_line[token_pos]; |
| 108 #if defined(DEBUG) | 107 #if defined(DEBUG) |
| 109 const Script& script = Script::Handle(zone, function.script()); | 108 const Script& script = Script::Handle(zone, function.script()); |
| (...skipping 24 matching lines...) Expand all Loading... |
| 134 hits_or_sites.AddValue(last_count); | 133 hits_or_sites.AddValue(last_count); |
| 135 } | 134 } |
| 136 } | 135 } |
| 137 | 136 |
| 138 | 137 |
| 139 void CodeCoverage::PrintClass(const Library& lib, | 138 void CodeCoverage::PrintClass(const Library& lib, |
| 140 const Class& cls, | 139 const Class& cls, |
| 141 const JSONArray& jsarr, | 140 const JSONArray& jsarr, |
| 142 CoverageFilter* filter, | 141 CoverageFilter* filter, |
| 143 bool as_call_sites) { | 142 bool as_call_sites) { |
| 144 Isolate* isolate = Isolate::Current(); | 143 Thread* thread = Thread::Current(); |
| 144 Isolate* isolate = thread->isolate(); |
| 145 if (cls.EnsureIsFinalized(isolate) != Error::null()) { | 145 if (cls.EnsureIsFinalized(isolate) != Error::null()) { |
| 146 // Only classes that have been finalized do have a meaningful list of | 146 // Only classes that have been finalized do have a meaningful list of |
| 147 // functions. | 147 // functions. |
| 148 return; | 148 return; |
| 149 } | 149 } |
| 150 Array& functions = Array::Handle(cls.functions()); | 150 Array& functions = Array::Handle(cls.functions()); |
| 151 ASSERT(!functions.IsNull()); | 151 ASSERT(!functions.IsNull()); |
| 152 Function& function = Function::Handle(); | 152 Function& function = Function::Handle(); |
| 153 Script& script = Script::Handle(); | 153 Script& script = Script::Handle(); |
| 154 String& saved_url = String::Handle(); | 154 String& saved_url = String::Handle(); |
| 155 String& url = String::Handle(); | 155 String& url = String::Handle(); |
| 156 GrowableArray<intptr_t> pos_to_line; | 156 GrowableArray<intptr_t> pos_to_line; |
| 157 int i = 0; | 157 int i = 0; |
| 158 while (i < functions.Length()) { | 158 while (i < functions.Length()) { |
| 159 HANDLESCOPE(isolate); | 159 HANDLESCOPE(thread); |
| 160 function ^= functions.At(i); | 160 function ^= functions.At(i); |
| 161 script = function.script(); | 161 script = function.script(); |
| 162 saved_url = script.url(); | 162 saved_url = script.url(); |
| 163 if (!filter->ShouldOutputCoverageFor(lib, script, cls, function)) { | 163 if (!filter->ShouldOutputCoverageFor(lib, script, cls, function)) { |
| 164 i++; | 164 i++; |
| 165 continue; | 165 continue; |
| 166 } | 166 } |
| 167 ComputeTokenPosToLineNumberMap(script, &pos_to_line); | 167 ComputeTokenPosToLineNumberMap(script, &pos_to_line); |
| 168 JSONObject jsobj(&jsarr); | 168 JSONObject jsobj(&jsarr); |
| 169 jsobj.AddProperty("source", saved_url.ToCString()); | 169 jsobj.AddProperty("source", saved_url.ToCString()); |
| (...skipping 24 matching lines...) Expand all Loading... |
| 194 } | 194 } |
| 195 | 195 |
| 196 GrowableObjectArray& closures = | 196 GrowableObjectArray& closures = |
| 197 GrowableObjectArray::Handle(cls.closures()); | 197 GrowableObjectArray::Handle(cls.closures()); |
| 198 if (!closures.IsNull()) { | 198 if (!closures.IsNull()) { |
| 199 i = 0; | 199 i = 0; |
| 200 pos_to_line.Clear(); | 200 pos_to_line.Clear(); |
| 201 // We need to keep rechecking the length of the closures array, as handling | 201 // We need to keep rechecking the length of the closures array, as handling |
| 202 // a closure potentially adds new entries to the end. | 202 // a closure potentially adds new entries to the end. |
| 203 while (i < closures.Length()) { | 203 while (i < closures.Length()) { |
| 204 HANDLESCOPE(isolate); | 204 HANDLESCOPE(thread); |
| 205 function ^= closures.At(i); | 205 function ^= closures.At(i); |
| 206 script = function.script(); | 206 script = function.script(); |
| 207 saved_url = script.url(); | 207 saved_url = script.url(); |
| 208 if (!filter->ShouldOutputCoverageFor(lib, script, cls, function)) { | 208 if (!filter->ShouldOutputCoverageFor(lib, script, cls, function)) { |
| 209 i++; | 209 i++; |
| 210 continue; | 210 continue; |
| 211 } | 211 } |
| 212 ComputeTokenPosToLineNumberMap(script, &pos_to_line); | 212 ComputeTokenPosToLineNumberMap(script, &pos_to_line); |
| 213 JSONObject jsobj(&jsarr); | 213 JSONObject jsobj(&jsarr); |
| 214 jsobj.AddProperty("source", saved_url.ToCString()); | 214 jsobj.AddProperty("source", saved_url.ToCString()); |
| (...skipping 73 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 288 cls = it.GetNextClass(); | 288 cls = it.GetNextClass(); |
| 289 ASSERT(!cls.IsNull()); | 289 ASSERT(!cls.IsNull()); |
| 290 PrintClass(lib, cls, jsarr, filter, as_call_sites); | 290 PrintClass(lib, cls, jsarr, filter, as_call_sites); |
| 291 } | 291 } |
| 292 } | 292 } |
| 293 } | 293 } |
| 294 } | 294 } |
| 295 | 295 |
| 296 | 296 |
| 297 } // namespace dart | 297 } // namespace dart |
| OLD | NEW |