如何在没有记忆泄漏的情况下捕获铁锈信号

发布于 2025-02-05 03:15:05 字数 1736 浏览 0 评论 0原文

我注意到程序中的内存泄漏,并将其跟踪到信号处理。似乎没有一种无泄漏的方法来做到这一点。我不担心Valgrind报告的“仍然可以达到的”字节 - 我担心“可能丢失”字节。

最小可重复的示例:

use tokio::signal;
use tokio::time::{sleep, Duration};

async fn sleep1() {
    loop {
        sleep(Duration::from_secs(1)).await;
        println!("sleep1");
    }
}

async fn sleep2() {
    loop {
        sleep(Duration::from_secs(2)).await;
        println!("sleep2");
    }
}

#[tokio::main]
async fn main() -> Result<(), Box<dyn std::error::Error>> {
    let s1 = Box::pin(sleep1());
    let s2 = Box::pin(sleep2());
    let sig = Box::pin(signal::ctrl_c());
    tokio::select! {
        _ = s1 => {},
        _ = s2 => {},
        _ = sig => {},
    };
    println!("shutting down");
    Ok(())
}

摘录摘自货物。汤姆尔文件:

edition = "2021"
tokio = { version = "1", features = ["full"] }

valgrind输出:

==1366460== Command: target/debug/simulation
==1366460== 
sleep1
sleep2
sleep1
sleep1
^Cshutting down
==1366460== 
==1366460== HEAP SUMMARY:
==1366460==     in use at exit: 25,884 bytes in 82 blocks
==1366460==   total heap usage: 617 allocs, 535 frees, 145,635 bytes allocated
==1366460== 
==1366460== LEAK SUMMARY:
==1366460==    definitely lost: 0 bytes in 0 blocks
==1366460==    indirectly lost: 0 bytes in 0 blocks
==1366460==      possibly lost: 1,188 bytes in 3 blocks
==1366460==    still reachable: 24,696 bytes in 79 blocks
==1366460==         suppressed: 0 bytes in 0 blocks
==1366460== Rerun with --leak-check=full to see details of leaked memory
==1366460== 
==1366460== For lists of detected and suppressed errors, rerun with: -s
==1366460== ERROR SUMMARY: 0 errors from 0 contexts (suppressed: 0 from 0)

I noticed memory leaks in my program and tracked it down to the signal handling. Seems crazy that there isn't a leak-free way to do this. I'm not worried about the "still reachable" bytes reported by Valgrind - I'm worried about the "possibly lost" bytes.

minimal reproducible example:

use tokio::signal;
use tokio::time::{sleep, Duration};

async fn sleep1() {
    loop {
        sleep(Duration::from_secs(1)).await;
        println!("sleep1");
    }
}

async fn sleep2() {
    loop {
        sleep(Duration::from_secs(2)).await;
        println!("sleep2");
    }
}

#[tokio::main]
async fn main() -> Result<(), Box<dyn std::error::Error>> {
    let s1 = Box::pin(sleep1());
    let s2 = Box::pin(sleep2());
    let sig = Box::pin(signal::ctrl_c());
    tokio::select! {
        _ = s1 => {},
        _ = s2 => {},
        _ = sig => {},
    };
    println!("shutting down");
    Ok(())
}

excerpt from Cargo.toml file:

edition = "2021"
tokio = { version = "1", features = ["full"] }

valgrind output:

==1366460== Command: target/debug/simulation
==1366460== 
sleep1
sleep2
sleep1
sleep1
^Cshutting down
==1366460== 
==1366460== HEAP SUMMARY:
==1366460==     in use at exit: 25,884 bytes in 82 blocks
==1366460==   total heap usage: 617 allocs, 535 frees, 145,635 bytes allocated
==1366460== 
==1366460== LEAK SUMMARY:
==1366460==    definitely lost: 0 bytes in 0 blocks
==1366460==    indirectly lost: 0 bytes in 0 blocks
==1366460==      possibly lost: 1,188 bytes in 3 blocks
==1366460==    still reachable: 24,696 bytes in 79 blocks
==1366460==         suppressed: 0 bytes in 0 blocks
==1366460== Rerun with --leak-check=full to see details of leaked memory
==1366460== 
==1366460== For lists of detected and suppressed errors, rerun with: -s
==1366460== ERROR SUMMARY: 0 errors from 0 contexts (suppressed: 0 from 0)

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

零崎曲识 2025-02-12 03:15:06

根据Tokio开发人员的说法,这是使用全局变量的假阳性。参见在这里

另外,我发现,如果一个人真的希望摆脱valgrind错误,则有可能 and 从rust 称呼它。 RUST程序将产生一个阻止线程(例如Tokio :: tos :: Spawn_blocking),该线程等待C代码捕获信号并终止。

according to the tokio developers, this is a false positive resulting from the use of global variables. see here.

also, I found that if one really wishes to get rid of the valgrind error, it's possible to implement the signal handler in C and call it from rust. The rust program would spawn a blocking thread (something like tokio::task::spawn_blocking) that waits for the C code to catch a signal and terminate.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文