blob: 9576f4b341460f00c59219dd803c788ab54f7ef7 [file] [log] [blame]
Mathieu Chartiere5f13e52015-02-24 09:37:21 -08001/*
2 * Copyright 2014 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17#ifndef ART_RUNTIME_JIT_JIT_INSTRUMENTATION_H_
18#define ART_RUNTIME_JIT_JIT_INSTRUMENTATION_H_
19
20#include <unordered_map>
21
22#include "instrumentation.h"
23
24#include "atomic.h"
25#include "base/macros.h"
26#include "base/mutex.h"
27#include "gc_root.h"
28#include "jni.h"
29#include "object_callbacks.h"
30#include "thread_pool.h"
31
32namespace art {
33namespace mirror {
34 class ArtField;
35 class ArtMethod;
36 class Class;
37 class Object;
38 class Throwable;
39} // namespace mirror
40union JValue;
41class Thread;
42class ThrowLocation;
43
44namespace jit {
45
46// Keeps track of which methods are hot.
47class JitInstrumentationCache {
48 public:
49 explicit JitInstrumentationCache(size_t hot_method_threshold);
50 void AddSamples(Thread* self, mirror::ArtMethod* method, size_t samples)
51 SHARED_LOCKS_REQUIRED(Locks::mutator_lock_);
52 void SignalCompiled(Thread* self, mirror::ArtMethod* method)
53 SHARED_LOCKS_REQUIRED(Locks::mutator_lock_);
54 void CreateThreadPool();
55 void DeleteThreadPool();
56
57 private:
58 Mutex lock_;
59 std::unordered_map<jmethodID, size_t> samples_;
60 size_t hot_method_threshold_;
61 std::unique_ptr<ThreadPool> thread_pool_;
62};
63
64class JitInstrumentationListener : public instrumentation::InstrumentationListener {
65 public:
66 explicit JitInstrumentationListener(JitInstrumentationCache* cache);
67
68 virtual void MethodEntered(Thread* thread, mirror::Object* /*this_object*/,
69 mirror::ArtMethod* method, uint32_t /*dex_pc*/)
70 OVERRIDE SHARED_LOCKS_REQUIRED(Locks::mutator_lock_) {
71 instrumentation_cache_->AddSamples(thread, method, 1);
72 }
73 virtual void MethodExited(Thread* /*thread*/, mirror::Object* /*this_object*/,
74 mirror::ArtMethod* /*method*/, uint32_t /*dex_pc*/,
75 const JValue& /*return_value*/)
76 OVERRIDE { }
77 virtual void MethodUnwind(Thread* /*thread*/, mirror::Object* /*this_object*/,
78 mirror::ArtMethod* /*method*/, uint32_t /*dex_pc*/) OVERRIDE { }
79 virtual void FieldRead(Thread* /*thread*/, mirror::Object* /*this_object*/,
80 mirror::ArtMethod* /*method*/, uint32_t /*dex_pc*/,
81 mirror::ArtField* /*field*/) OVERRIDE { }
82 virtual void FieldWritten(Thread* /*thread*/, mirror::Object* /*this_object*/,
83 mirror::ArtMethod* /*method*/, uint32_t /*dex_pc*/,
84 mirror::ArtField* /*field*/, const JValue& /*field_value*/)
85 OVERRIDE { }
86 virtual void ExceptionCaught(Thread* /*thread*/, const ThrowLocation& /*throw_location*/,
87 mirror::ArtMethod* /*catch_method*/, uint32_t /*catch_dex_pc*/,
88 mirror::Throwable* /*exception_object*/) OVERRIDE { }
89
90 virtual void DexPcMoved(Thread* /*self*/, mirror::Object* /*this_object*/,
91 mirror::ArtMethod* /*method*/, uint32_t /*new_dex_pc*/) OVERRIDE { }
92
93 // We only care about how many dex instructions were executed in the Jit.
94 virtual void BackwardBranch(Thread* thread, mirror::ArtMethod* method, int32_t dex_pc_offset)
95 OVERRIDE SHARED_LOCKS_REQUIRED(Locks::mutator_lock_) {
96 CHECK_LE(dex_pc_offset, 0);
97 instrumentation_cache_->AddSamples(thread, method, 1);
98 }
99
100 private:
101 JitInstrumentationCache* const instrumentation_cache_;
102};
103
104} // namespace jit
105} // namespace art
106
107#endif // ART_RUNTIME_JIT_JIT_INSTRUMENTATION_H_