#flame-graph #intrusive #low-overhead #profiler #firestorm #instrumenting

firestorm-enabled

Firestorm的依赖项。请勿直接使用。

7 个版本

0.5.1 2022年5月20日
0.5.0 2021年8月11日
0.4.3 2021年3月31日
0.4.2 2021年2月23日
0.3.1 2021年2月13日

#298 in 性能分析

Download history 63/week @ 2024-03-11 53/week @ 2024-03-18 114/week @ 2024-04-01 34/week @ 2024-04-08 37/week @ 2024-04-15 65/week @ 2024-04-22 38/week @ 2024-04-29 38/week @ 2024-05-06 31/week @ 2024-05-13 51/week @ 2024-05-20 41/week @ 2024-05-27 44/week @ 2024-06-03 45/week @ 2024-06-10 37/week @ 2024-06-17 49/week @ 2024-06-24

每月下载 180
2 个库中使用(通过 firestorm

MIT 许可协议

18KB
344

Firestorm是Rust的低开销侵入式火焰图性能分析器。

Crates.io Documentation MIT licensed

设计原则

对于配置,从这里开始

对于性能分析,从这里开始

Firestorm在底层使用inferno来显示火焰图。没有他们的贡献,Firestorm将无法实现。


设计原则

Firestorm注重性能。当你编写一个在其类别中速度最快的库时,你需要一个具有相同理想的性能分析器。当Firestorm未启用(默认情况)时,所有调用都会编译为空操作。当Firestorm启用时,它不进行堆分配,并在关键部分中避免尽可能多的工作。

Firestorm无处不在。当应用程序层启用Firestorm进行性能分析时,它会对所有依赖项进行递归启用。这不需要向库中添加功能标志,甚至不需要知道哪些库使用Firestorm。通过避免将Firestorm作为库的公共API的一部分,再加上Firestorm在未使用时编译为空操作的事实...将Firestorm添加到库中应该是一个简单的问题。这是因为随着更多库采用Firestorm,应用程序也会从中受益。

Firestorm提供洞察力。在分析后,Firestorm提供了三种不同的方式来查看数据 - 每种方式都从不同的角度查看运行性能。


配置

首先,在Cargo.toml中将Firestorm添加到您的依赖项中

[dependencies]
firestorm = "0.4"

然后,导入Firestorm的性能宏。我建议在crate prelude 模块中这样做。

pub(crate) use firestorm::{
    profile_fn,
    profile_method,
    profile_section
};

最后,在您的函数中调用宏。

fn fn_name<T>(param: T) {
    // Call profile_fn at the top of your function, specifying the function name.
    // You can optionally add generic parameters, too
    profile_fn!(T, fn_name);

    // If a function is complex, profile a section.
    {
        profile_section!(inner);

        // Optional: manually drop.
        // Section automatically drops when going out of scope.
        drop(inner);
    }
}

fn method_name(&self) {
    // profile_method automatically captures the type of Self
    profile_method!(method_name);
}

配置库的重要提示

  • 不要针对Firestorm的确切版本。例如:不要使用firestorm = "=0.4.1"。请使用firestorm = "0.4.1"代替。这是Firestorm向后兼容策略的重要组成部分。如果需要更新firestorm-core,所有主要版本都将收到补丁,以便所有版本的Firestorm都能启用。针对特定版本可能会阻止库共享firestorm-core依赖项或递归启用。
  • 不要将firestorm放入[dev-dependencies]。始终将firestorm放入[dependencies]
  • 不要在库代码中启用任何firestorm功能,例如enable_system_time。这样做将阻止Firestorm在不使用时编译为无操作。
  • 不要在功能标志或[cfg()]之后隐藏Firestorm的使用。Firestorm应始终处于使用状态,除非启用,否则不会影响编译时间或性能。

性能分析

要启用性能分析,Firestorm需要在Cargo.toml中指定一个附加功能。

[dependencies]
firestorm = { version="0.4", features=["enable_system_time"] }

分析会话并保存结果

// Runs the function and saves the flamegraph to the supplied directory.
// Make sure this is an empty directory so that no important files are overwritten.
if firestorm::enabled() {
    firestorm::bench("./flames/", instrumented_function).unwrap();
}

运行上述命令后,目标目录中会有一个firestorm.html文件和一个包含支持文件的/firestorm子目录。打开firestorm.html以查看结果。

有三个输出火焰图以不同的方式聚合数据。左上角的下拉菜单切换模式。

时间轴

Time Axis

此模式为每个函数的每次调用显示一个单独的条形图。它被称为“时间轴”,因为数据就像y轴是时间一样。如果想要区分对函数的许多短调用与一次长调用,这将特别有用。这包含了最多的信息,但可能会有些嘈杂。

合并

Merged

此模式为调用堆栈中的每条路径显示一个条形图。多个调用可以在单个条形图中显示。这聚合了更多信息。与时间轴模式类似,条形图的宽度表示函数的总时间 - 包括自有时长和被调用函数的时间。

自有时长

Own Time

此模式将每个函数的自有时长以侧向条形图的形式显示,而不管它是由谁调用的。排序是最耗时的在底部,而“堆栈”与哪个函数调用其他函数无关。遗憾的是,我们的火焰图依赖项不理解这一点,所以请忽略那部分。Firestorm应该改进这里的显示方法,但考虑到它在这个第一版中的有用性,我们决定保留。

依赖项

~3–11MB
~99K SLoC