1 /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*-
2  * vim: set ts=8 sts=2 et sw=2 tw=80:
3  * This Source Code Form is subject to the terms of the Mozilla Public
4  * License, v. 2.0. If a copy of the MPL was not distributed with this
5  * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
6 
7 #ifndef jit_PerfSpewer_h
8 #define jit_PerfSpewer_h
9 
10 #ifdef JS_ION_PERF
11 #  include <stdio.h>
12 #  include "jit/MacroAssembler.h"
13 #endif
14 
15 namespace {
16 struct AutoLockPerfMap;
17 }
18 
19 namespace js {
20 namespace jit {
21 
22 class MBasicBlock;
23 class MacroAssembler;
24 
25 #ifdef JS_ION_PERF
26 void CheckPerf();
27 bool PerfBlockEnabled();
28 bool PerfFuncEnabled();
PerfEnabled()29 static inline bool PerfEnabled() {
30   return PerfBlockEnabled() || PerfFuncEnabled();
31 }
32 #else
CheckPerf()33 static inline void CheckPerf() {}
PerfBlockEnabled()34 static inline bool PerfBlockEnabled() { return false; }
PerfFuncEnabled()35 static inline bool PerfFuncEnabled() { return false; }
PerfEnabled()36 static inline bool PerfEnabled() { return false; }
37 #endif
38 
39 #ifdef JS_ION_PERF
40 
41 struct Record {
42   const char* filename;
43   unsigned lineNumber;
44   unsigned columnNumber;
45   uint32_t id;
46   Label start, end;
47   size_t startOffset, endOffset;
48 
RecordRecord49   Record(const char* filename, unsigned lineNumber, unsigned columnNumber,
50          uint32_t id)
51       : filename(filename),
52         lineNumber(lineNumber),
53         columnNumber(columnNumber),
54         id(id),
55         startOffset(0u),
56         endOffset(0u) {}
57 };
58 
59 typedef Vector<Record, 1, SystemAllocPolicy> BasicBlocksVector;
60 
61 class PerfSpewer {
62  protected:
63   static uint32_t nextFunctionIndex;
64 
65  public:
66   Label endInlineCode;
67 
68  protected:
69   BasicBlocksVector basicBlocks_;
70 
71  public:
72   virtual MOZ_MUST_USE bool startBasicBlock(MBasicBlock* blk,
73                                             MacroAssembler& masm);
74   virtual void endBasicBlock(MacroAssembler& masm);
75   void noteEndInlineCode(MacroAssembler& masm);
76 
77   void writeProfile(JSScript* script, JitCode* code, MacroAssembler& masm);
78 
79   static void WriteEntry(const AutoLockPerfMap&, uintptr_t address, size_t size,
80                          const char* fmt, ...) MOZ_FORMAT_PRINTF(4, 5);
81 };
82 
83 void writePerfSpewerBaselineProfile(JSScript* script, JitCode* code);
84 void writePerfSpewerJitCodeProfile(JitCode* code, const char* msg);
85 
86 // wasm doesn't support block annotations.
87 class WasmPerfSpewer : public PerfSpewer {
88  public:
startBasicBlock(MBasicBlock * blk,MacroAssembler & masm)89   MOZ_MUST_USE bool startBasicBlock(MBasicBlock* blk, MacroAssembler& masm) {
90     return true;
91   }
endBasicBlock(MacroAssembler & masm)92   void endBasicBlock(MacroAssembler& masm) {}
93 };
94 
95 void writePerfSpewerWasmMap(uintptr_t base, uintptr_t size,
96                             const char* filename, const char* annotation);
97 void writePerfSpewerWasmFunctionMap(uintptr_t base, uintptr_t size,
98                                     const char* filename, unsigned lineno,
99                                     const char* funcName);
100 
101 #endif  // JS_ION_PERF
102 
103 }  // namespace jit
104 }  // namespace js
105 
106 #endif /* jit_PerfSpewer_h */
107