Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Commit 362aa43

Browse files
authored
[mlir] Enhance TimingManager Printing Flexibility (llvm#85821)
Revise the printing functionality of TimingManager to accommodate various output formats. At present, TimingManager is limited to outputting data solely in plain text format. To overcome this limitation, I have introduced an abstract class that serves as the foundation for printing. This approach allows users to implement additional output formats by extending this abstract class. As part of this update, I have integrated support for JSON as a new output format, enhancing the ease of parsing for subsequent processing scripts.
1 parent a77d3d9 commit 362aa43

File tree

4 files changed

+297
-94
lines changed

4 files changed

+297
-94
lines changed

mlir/docs/PassManagement.md

+78-24
Original file line numberDiff line numberDiff line change
@@ -1124,17 +1124,44 @@ pipeline. This display mode is available in mlir-opt via
11241124
$ mlir-opt foo.mlir -mlir-disable-threading -pass-pipeline='builtin.module(func.func(cse,canonicalize),convert-func-to-llvm)' -mlir-timing -mlir-timing-display=list
11251125
11261126
===-------------------------------------------------------------------------===
1127-
... Pass execution timing report ...
1127+
... Execution time report ...
11281128
===-------------------------------------------------------------------------===
1129-
Total Execution Time: 0.0203 seconds
1130-
1131-
---Wall Time--- --- Name ---
1132-
0.0047 ( 55.9%) Canonicalizer
1133-
0.0019 ( 22.2%) VerifierPass
1134-
0.0016 ( 18.5%) LLVMLoweringPass
1135-
0.0003 ( 3.4%) CSE
1136-
0.0002 ( 1.9%) (A) DominanceInfo
1137-
0.0084 (100.0%) Total
1129+
Total Execution Time: 0.0135 seconds
1130+
1131+
----Wall Time---- ----Name----
1132+
0.0135 (100.0%) root
1133+
0.0041 ( 30.1%) Parser
1134+
0.0018 ( 13.3%) ConvertFuncToLLVMPass
1135+
0.0011 ( 8.2%) Output
1136+
0.0007 ( 5.2%) Pipeline Collection : ['func.func']
1137+
0.0006 ( 4.6%) 'func.func' Pipeline
1138+
0.0005 ( 3.5%) Canonicalizer
1139+
0.0001 ( 0.9%) CSE
1140+
0.0001 ( 0.5%) (A) DataLayoutAnalysis
1141+
0.0000 ( 0.1%) (A) DominanceInfo
1142+
0.0058 ( 43.2%) Rest
1143+
0.0135 (100.0%) Total
1144+
```
1145+
1146+
The results can be displayed in JSON format via `-mlir-output-format=json`.
1147+
1148+
```shell
1149+
$ mlir-opt foo.mlir -mlir-disable-threading -pass-pipeline='builtin.module(func.func(cse,canonicalize),convert-func-to-llvm)' -mlir-timing -mlir-timing-display=list -mlir-output-format=json
1150+
1151+
[
1152+
{"wall": {"duration": 0.0135, "percentage": 100.0}, "name": "root"},
1153+
{"wall": {"duration": 0.0041, "percentage": 30.1}, "name": "Parser"},
1154+
{"wall": {"duration": 0.0018, "percentage": 13.3}, "name": "ConvertFuncToLLVMPass"},
1155+
{"wall": {"duration": 0.0011, "percentage": 8.2}, "name": "Output"},
1156+
{"wall": {"duration": 0.0007, "percentage": 5.2}, "name": "Pipeline Collection : ['func.func']"},
1157+
{"wall": {"duration": 0.0006, "percentage": 4.6}, "name": "'func.func' Pipeline"},
1158+
{"wall": {"duration": 0.0005, "percentage": 3.5}, "name": "Canonicalizer"},
1159+
{"wall": {"duration": 0.0001, "percentage": 0.9}, "name": "CSE"},
1160+
{"wall": {"duration": 0.0001, "percentage": 0.5}, "name": "(A) DataLayoutAnalysis"},
1161+
{"wall": {"duration": 0.0000, "percentage": 0.1}, "name": "(A) DominanceInfo"},
1162+
{"wall": {"duration": 0.0058, "percentage": 43.2}, "name": "Rest"},
1163+
{"wall": {"duration": 0.0135, "percentage": 100.0}, "name": "Total"}
1164+
]
11381165
```
11391166

11401167
##### Tree Display Mode
@@ -1149,21 +1176,48 @@ invalidated and recomputed. This is the default display mode.
11491176
$ mlir-opt foo.mlir -mlir-disable-threading -pass-pipeline='builtin.module(func.func(cse,canonicalize),convert-func-to-llvm)' -mlir-timing
11501177

11511178
===-------------------------------------------------------------------------===
1152-
... Pass execution timing report ...
1179+
... Execution time report ...
11531180
===-------------------------------------------------------------------------===
1154-
Total Execution Time: 0.0249 seconds
1155-
1156-
---Wall Time--- --- Name ---
1157-
0.0058 ( 70.8%) 'func.func' Pipeline
1158-
0.0004 ( 4.3%) CSE
1159-
0.0002 ( 2.6%) (A) DominanceInfo
1160-
0.0004 ( 4.8%) VerifierPass
1161-
0.0046 ( 55.4%) Canonicalizer
1162-
0.0005 ( 6.2%) VerifierPass
1163-
0.0005 ( 5.8%) VerifierPass
1164-
0.0014 ( 17.2%) LLVMLoweringPass
1165-
0.0005 ( 6.2%) VerifierPass
1166-
0.0082 (100.0%) Total
1181+
Total Execution Time: 0.0127 seconds
1182+
1183+
----Wall Time---- ----Name----
1184+
0.0038 ( 30.2%) Parser
1185+
0.0006 ( 4.8%) 'func.func' Pipeline
1186+
0.0001 ( 0.9%) CSE
1187+
0.0000 ( 0.1%) (A) DominanceInfo
1188+
0.0005 ( 3.7%) Canonicalizer
1189+
0.0017 ( 13.7%) ConvertFuncToLLVMPass
1190+
0.0001 ( 0.6%) (A) DataLayoutAnalysis
1191+
0.0010 ( 8.2%) Output
1192+
0.0054 ( 42.5%) Rest
1193+
0.0127 (100.0%) Total
1194+
```
1195+
1196+
The results can be displayed in JSON format via `-mlir-output-format=json`.
1197+
1198+
```shell
1199+
$ mlir-opt foo.mlir -mlir-disable-threading -pass-pipeline='builtin.module(func.func(cse,canonicalize),convert-func-to-llvm)' -mlir-timing -mlir-output-format=json
1200+
1201+
[
1202+
{"wall": {"duration": 0.0038, "percentage": 30.2}, "name": "Parser", "passes": [
1203+
{}]},
1204+
{"wall": {"duration": 0.0006, "percentage": 4.8}, "name": "'func.func' Pipeline", "passes": [
1205+
{"wall": {"duration": 0.0001, "percentage": 0.9}, "name": "CSE", "passes": [
1206+
{"wall": {"duration": 0.0000, "percentage": 0.1}, "name": "(A) DominanceInfo", "passes": [
1207+
{}]},
1208+
{}]},
1209+
{"wall": {"duration": 0.0005, "percentage": 3.7}, "name": "Canonicalizer", "passes": [
1210+
{}]},
1211+
{}]},
1212+
{"wall": {"duration": 0.0017, "percentage": 13.7}, "name": "ConvertFuncToLLVMPass", "passes": [
1213+
{"wall": {"duration": 0.0001, "percentage": 0.6}, "name": "(A) DataLayoutAnalysis", "passes": [
1214+
{}]},
1215+
{}]},
1216+
{"wall": {"duration": 0.0010, "percentage": 8.2}, "name": "Output", "passes": [
1217+
{}]},
1218+
{"wall": {"duration": 0.0054, "percentage": 42.5}, "name": "Rest"},
1219+
{"wall": {"duration": 0.0127, "percentage": 100.0}, "name": "Total"}
1220+
]
11671221
```
11681222

11691223
##### Multi-threaded Pass Timing

mlir/include/mlir/Support/Timing.h

+58-4
Original file line numberDiff line numberDiff line change
@@ -320,6 +320,53 @@ class TimingScope {
320320
Timer timer;
321321
};
322322

323+
//===----------------------------------------------------------------------===//
324+
// OutputStrategy
325+
//===----------------------------------------------------------------------===//
326+
327+
/// Simple record class to record timing information.
328+
struct TimeRecord {
329+
TimeRecord(double wall = 0.0, double user = 0.0) : wall(wall), user(user) {}
330+
331+
TimeRecord &operator+=(const TimeRecord &other) {
332+
wall += other.wall;
333+
user += other.user;
334+
return *this;
335+
}
336+
337+
TimeRecord &operator-=(const TimeRecord &other) {
338+
wall -= other.wall;
339+
user -= other.user;
340+
return *this;
341+
}
342+
343+
double wall, user;
344+
};
345+
346+
/// Facilities for printing timing reports to various output formats.
347+
///
348+
/// This is an abstract class that serves as the foundation for printing.
349+
/// Users can implement additional output formats by extending this abstract
350+
/// class.
351+
class OutputStrategy {
352+
public:
353+
OutputStrategy(raw_ostream &os) : os(os) {}
354+
virtual ~OutputStrategy() = default;
355+
356+
virtual void printHeader(const TimeRecord &total) = 0;
357+
virtual void printFooter() = 0;
358+
virtual void printTime(const TimeRecord &time, const TimeRecord &total) = 0;
359+
virtual void printListEntry(StringRef name, const TimeRecord &time,
360+
const TimeRecord &total,
361+
bool lastEntry = false) = 0;
362+
virtual void printTreeEntry(unsigned indent, StringRef name,
363+
const TimeRecord &time,
364+
const TimeRecord &total) = 0;
365+
virtual void printTreeEntryEnd(unsigned indent, bool lastEntry = false) = 0;
366+
367+
raw_ostream &os;
368+
};
369+
323370
//===----------------------------------------------------------------------===//
324371
// DefaultTimingManager
325372
//===----------------------------------------------------------------------===//
@@ -351,6 +398,15 @@ class DefaultTimingManager : public TimingManager {
351398
Tree,
352399
};
353400

401+
/// The different output formats for printing the timers.
402+
enum class OutputFormat {
403+
/// In this format the results are displayed in text format.
404+
Text,
405+
406+
/// In this format the results are displayed in JSON format.
407+
Json,
408+
};
409+
354410
DefaultTimingManager();
355411
DefaultTimingManager(DefaultTimingManager &&rhs);
356412
~DefaultTimingManager() override;
@@ -372,10 +428,7 @@ class DefaultTimingManager : public TimingManager {
372428
DisplayMode getDisplayMode() const;
373429

374430
/// Change the stream where the output will be printed to.
375-
void setOutput(raw_ostream &os);
376-
377-
/// Return the current output stream where the output will be printed to.
378-
raw_ostream &getOutput() const;
431+
void setOutput(std::unique_ptr<OutputStrategy> output);
379432

380433
/// Print and clear the timing results. Only call this when there are no more
381434
/// references to nested timers around, as printing post-processes and clears
@@ -408,6 +461,7 @@ class DefaultTimingManager : public TimingManager {
408461

409462
private:
410463
const std::unique_ptr<detail::DefaultTimingManagerImpl> impl;
464+
std::unique_ptr<OutputStrategy> out;
411465
};
412466

413467
/// Register a set of useful command-line options that can be used to configure

0 commit comments

Comments
 (0)