繁体   English   中英

货物测试-释放导致堆栈溢出。 为什么没有货台?

[英]cargo test --release causes a stack overflow. Why doesn't cargo bench?

在尝试编写优化的DSP算法时,我想知道堆栈分配和堆分配之间的相对速度以及堆栈分配数组的大小限制。 我意识到有一个堆栈框架大小限制,但是我不明白为什么要运行以下程序,从而在cargo bench产生看似真实的基准测试结果,但是在进行cargo test --release时出现堆栈溢出失败。

#![feature(test)]
extern crate test;

#[cfg(test)]
mod tests {
    use test::Bencher;

    #[bench]
    fn it_works(b: &mut Bencher) {
        b.iter(|| { let stack = [[[0.0; 2]; 512]; 512]; });
    }
}

为了让您更直观,请注意,阵列的大小为8×2×512×512 = 4 MiB。

cargo test崩溃,但cargo test cargo bench没有崩溃,因为“测试” 在新线程中调用了函数it_works() ,而“长凳” 在主线程中调用了该函数。

主线程的默认堆栈大小通常为8 MiB,因此该阵列将占据可用堆栈的一半。 足够多了,但仍有可用空间,因此基准测试正常运行。

但是, 新线程堆栈大小通常要小得多。 在Linux上是2 MiB, 其他平台可能更小 因此,您的4 MiB阵列很容易溢出线程的堆栈,并导致堆栈溢出/ segfault。

您可以通过设置RUST_MIN_STACK环境变量来增加新线程的默认堆栈大小。

$ RUST_MIN_STACK=8388608 cargo test 

cargo test测试在并行线程中运行测试以缩短总测试时间,而基准测试则在同一线程中依次运行以减少噪音。

由于堆栈大小有限,在堆栈上分配此数组是一个坏主意。 您必须将其存储在堆上( box )或作为全局static mut

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM