Lau*_*nce 9 multithreading rust
当我rustc 1.rs用来编译以下代码时,它会按预期无休止地运行.
use std::thread;
fn main() {
thread::spawn(|| {
let a = 2;
loop {
a*a;
}
}).join();
}
Run Code Online (Sandbox Code Playgroud)
更短的版本:
use std::thread;
fn main() {
thread::spawn(|| {
loop {}
}).join();
}
Run Code Online (Sandbox Code Playgroud)
但是,如果我rustc -O 1.rs用来编译上面的两个程序,它们会崩溃:
thread '<unnamed>' panicked at 'called `Result::unwrap()` on an `Err` value: Error { repr: Os { code: 0, message: "Success" } }', src/libcore/result.rs:837
stack backtrace:
1: 0x5650bd0acada - std::sys::imp::backtrace::tracing::imp::write::h917062bce4ff48c3
at /build/rustc-1.14.0+dfsg1/src/libstd/sys/unix/backtrace/tracing/gcc_s.rs:42
2: 0x5650bd0b068f - std::panicking::default_hook::{{closure}}::h0bacac31b5ed1870
at /build/rustc-1.14.0+dfsg1/src/libstd/panicking.rs:247
3: 0x5650bd0aee7c - std::panicking::default_hook::h5897799da33ece67
at /build/rustc-1.14.0+dfsg1/src/libstd/panicking.rs:263
4: 0x5650bd0af4d7 - std::panicking::rust_panic_with_hook::h109e116a3a861224
at /build/rustc-1.14.0+dfsg1/src/libstd/panicking.rs:451
5: 0x5650bd0af364 - std::panicking::begin_panic::hbb38be1379e09df0
at /build/rustc-1.14.0+dfsg1/src/libstd/panicking.rs:413
6: 0x5650bd0af289 - std::panicking::begin_panic_fmt::h26713cea9bce3ab0
at /build/rustc-1.14.0+dfsg1/src/libstd/panicking.rs:397
7: 0x5650bd0af217 - rust_begin_unwind
at /build/rustc-1.14.0+dfsg1/src/libstd/panicking.rs:373
8: 0x5650bd0e2f3d - core::panicking::panic_fmt::hcfbb59eeb7f27f75
at /build/rustc-1.14.0+dfsg1/src/libcore/panicking.rs:69
9: 0x5650bd0a6e84 - core::result::unwrap_failed::h15a0fc826f4081f4
10: 0x5650bd0b7ffa - __rust_maybe_catch_panic
at /build/rustc-1.14.0+dfsg1/src/libpanic_unwind/lib.rs:97
11: 0x5650bd0a6fc1 - <F as alloc::boxed::FnBox<A>>::call_box::he32a93ebea7bc7ad
12: 0x5650bd0ae6c4 - std::sys::imp::thread::Thread::new::thread_start::ha102a6120fc52763
at /build/rustc-1.14.0+dfsg1/src/liballoc/boxed.rs:605
at /build/rustc-1.14.0+dfsg1/src/libstd/sys_common/thread.rs:21
at /build/rustc-1.14.0+dfsg1/src/libstd/sys/unix/thread.rs:84
13: 0x7fc2d0042423 - start_thread
14: 0x7fc2cfb6e9be - __clone
15: 0x0 - <unknown>
Run Code Online (Sandbox Code Playgroud)
如果我删除闭包中的所有代码,它将退出并且没有错误:
use std::thread;
fn main() {
thread::spawn(|| {
}).join();
}
Run Code Online (Sandbox Code Playgroud)
如果我添加println!()循环,它也可以正常工作:
use std::thread;
fn main() {
thread::spawn(|| {
loop {
println!("123")
}
}).join();
}
Run Code Online (Sandbox Code Playgroud)
我在Rust 1.14和1.15上测试了这个,同样的问题出现在两者中.
这是因为我使用了什么错误或者它是一个错误?
这是一个已知问题(#28728).简而言之,LLVM优化了没有可观察到的副作用的循环:
实现可以假定任何线程最终将执行以下操作之一:
- 终止
- 调用库I/O函数
- 访问或修改易失性对象,或
- 执行同步操作或原子操作
在这种情况下,这些都不成立,因此LLVM完全删除了循环.但是,Rust编译器生成的代码假定循环永远不会返回.这种不匹配导致崩溃.
由于具有无副作用的无限循环基本上是无用的,因此该问题不是至关重要的.Rust团队目前正在等待LLVM提供更好的解决方案.
作为一种解决方法,你应该简单地在循环中做一些事情,这可能是你想做的事情^ _ ^
| 归档时间: |
|
| 查看次数: |
208 次 |
| 最近记录: |