首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >锈蚀堆叠溢出-在堆叠中寻找大型变数

锈蚀堆叠溢出-在堆叠中寻找大型变数
EN

Stack Overflow用户
提问于 2022-06-05 00:06:15
回答 1查看 272关注 0票数 0

我目前正经历一个非常可怕的堆栈溢出。

代码语言:javascript
复制
fn generate_all_possible_attacks_for(
    all_relevant_moves: &U64PerSquare,
    number_of_all_relevant_moves: &U64PerSquare,
    magic_numbers: &U64PerSquare,
    calculate_attacks_for: &dyn Fn(&dyn BoardPos, u64) -> u64,
) -> Box<[U64PerSquare; 4096]> {
    let mut all_attacks = Box::new([U64PerSquare::default(); 4096]);
    //...
}

我可以在函数本身上添加一个断点,但是就在之后(就像我在函数的第一行上放置了一个断点,或者添加了一个打印)永远不会到达,并且程序会经历堆栈溢出。

代码语言:javascript
复制
Exception thrown at 0x00007FF69C048067 in chess_ai.exe: 0xC00000FD: Stack overflow (parameters: 0x0000000000000001, 0x000000E296606000).

thread 'main' has overflowed its stack

由于堆栈跟踪本身相当短,因此我怀疑堆栈上放置了一些太大的变量:

代码语言:javascript
复制
chess_ai.exe!__chkstk() Line 109 (d:\a01\_work\6\s\src\vctools\crt\vcstartup\src\misc\amd64\chkstk.asm:109)
chess_ai.exe!chess_logic::magic_bit_board::generate_all_possible_attacks_for(unsigned __int64[64] * all_relevant_moves, unsigned __int64[64] * number_of_all_relevant_moves, unsigned __int64[64] * magic_numbers, ref$<dyn$<core::ops::function::Fn<tuple$<ref$<dyn$<chess_logic::square::BoardPos>>,u64>,assoc$<Output,u64>>>>) Line 302 (c:\Users\elias\Documents\Projects\chess_ai\chess_logic\src\magic_bit_board.rs:302)
chess_ai.exe!chess_logic::magic_bit_board::generate_all_possible_rook_attacks() Line 294 (c:\Users\elias\Documents\Projects\chess_ai\chess_logic\src\magic_bit_board.rs:294)
chess_ai.exe!core::ops::function::FnOnce::call_once<alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global> (*)(),tuple$<>>(unsigned __int64[4096][64] *(*)()) Line 227 (c:\rustc\fe5b13d681f25ee6474be29d748c65adcd91f69e\library\core\src\ops\function.rs:227)
chess_ai.exe!once_cell::sync::impl$11::force::closure$0<alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global>,alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global> (*)()>(once_cell::sync::impl$11::force::closure_env$0<alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global>,alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global> (*)()>) Line 1212 (c:\Users\elias\.cargo\registry\src\github.com-1ecc6299db9ec823\once_cell-1.12.0\src\lib.rs:1212)
chess_ai.exe!once_cell::sync::impl$6::get_or_init::closure$0<alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global>,once_cell::sync::impl$11::force::closure_env$0<alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global>,alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global> (*)()>>(once_cell::sync::impl$6::get_or_init::closure_env$0<alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global>,once_cell::sync::impl$11::force::closure_env$0<alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global>,alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global> (*)()>>) Line 1023 (c:\Users\elias\.cargo\registry\src\github.com-1ecc6299db9ec823\once_cell-1.12.0\src\lib.rs:1023)
chess_ai.exe!once_cell::imp::impl$4::initialize::closure$0<alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global>,once_cell::sync::impl$6::get_or_init::closure_env$0<alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global>,once_cell::sync::impl$11::force::closure_env$0<alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global>,alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global> (*)()>>,enum$<once_cell::sync::impl$6::get_or_init::Void>>(once_cell::imp::impl$4::initialize::closure_env$0<alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global>,once_cell::sync::impl$6::get_or_init::closure_env$0<alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global>,once_cell::sync::impl$11::force::closure_env$0<alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global>,alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global> (*)()>>,enum$<once_cell::sync::impl$6::get_or_init::Void>> *) Line 85 (c:\Users\elias\.cargo\registry\src\github.com-1ecc6299db9ec823\once_cell-1.12.0\src\imp_std.rs:85)
chess_ai.exe!core::ops::function::impls::impl$3::call_mut<tuple$<>,dyn$<core::ops::function::FnMut<tuple$<>,assoc$<Output,bool>>>>(ref_mut$<dyn$<core::ops::function::FnMut<tuple$<>,assoc$<Output,bool>>>> * self) Line 269 (c:\rustc\fe5b13d681f25ee6474be29d748c65adcd91f69e\library\core\src\ops\function.rs:269)
chess_ai.exe!once_cell::imp::initialize_or_wait(core::sync::atomic::AtomicUsize * queue, enum$<core::option::Option<ref_mut$<dyn$<core::ops::function::FnMut<tuple$<>,assoc$<Output,bool>>>>>, 1, 18446744073709551615, Some>) Line 213 (c:\Users\elias\.cargo\registry\src\github.com-1ecc6299db9ec823\once_cell-1.12.0\src\imp_std.rs:213)
chess_ai.exe!once_cell::imp::OnceCell<alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global>>::initialize<alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global>,once_cell::sync::impl$6::get_or_init::closure_env$0<alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global>,once_cell::sync::impl$11::force::closure_env$0<alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global>,alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global> (*)()>>,enum$<once_cell::sync::impl$6::get_or_init::Void>>(once_cell::sync::impl$6::get_or_init::closure_env$0<alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global>,once_cell::sync::impl$11::force::closure_env$0<alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global>,alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global> (*)()>> self) Line 81 (c:\Users\elias\.cargo\registry\src\github.com-1ecc6299db9ec823\once_cell-1.12.0\src\imp_std.rs:81)
chess_ai.exe!once_cell::sync::OnceCell<alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global>>::get_or_try_init<alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global>,once_cell::sync::impl$6::get_or_init::closure_env$0<alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global>,once_cell::sync::impl$11::force::closure_env$0<alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global>,alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global> (*)()>>,enum$<once_cell::sync::impl$6::get_or_init::Void>>(once_cell::sync::impl$6::get_or_init::closure_env$0<alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global>,once_cell::sync::impl$11::force::closure_env$0<alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global>,alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global> (*)()>> self) Line 1063 (c:\Users\elias\.cargo\registry\src\github.com-1ecc6299db9ec823\once_cell-1.12.0\src\lib.rs:1063)
chess_ai.exe!once_cell::sync::OnceCell<alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global>>::get_or_init<alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global>,once_cell::sync::impl$11::force::closure_env$0<alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global>,alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global> (*)()>>(once_cell::sync::impl$11::force::closure_env$0<alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global>,alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global> (*)()> self) Line 1023 (c:\Users\elias\.cargo\registry\src\github.com-1ecc6299db9ec823\once_cell-1.12.0\src\lib.rs:1023)
chess_ai.exe!once_cell::sync::Lazy<alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global>,alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global> (*)()>::force<alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global>,alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global> (*)()>() Line 1211 (c:\Users\elias\.cargo\registry\src\github.com-1ecc6299db9ec823\once_cell-1.12.0\src\lib.rs:1211)
chess_ai.exe!once_cell::sync::impl$12::deref<alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global>,alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global> (*)()>(once_cell::sync::Lazy<alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global>,alloc::boxed::Box<array$<array$<u64,64>,4096>,alloc::alloc::Global> (*)()> * self) Line 1221 (c:\Users\elias\.cargo\registry\src\github.com-1ecc6299db9ec823\once_cell-1.12.0\src\lib.rs:1221)
chess_ai.exe!chess_logic::magic_bit_board::get_rook_attacks_for(ref$<dyn$<chess_logic::square::BoardPos>> blockers, unsigned __int64) Line 48 (c:\Users\elias\Documents\Projects\chess_ai\chess_logic\src\magic_bit_board.rs:48)
chess_ai.exe!chess_ai::main() Line 19 (c:\Users\elias\Documents\Projects\chess_ai\src\main.rs:19)
chess_ai.exe!core::ops::function::FnOnce::call_once<void (*)(),tuple$<>>(void(*)()) Line 227 (c:\rustc\fe5b13d681f25ee6474be29d748c65adcd91f69e\library\core\src\ops\function.rs:227)
chess_ai.exe!std::sys_common::backtrace::__rust_begin_short_backtrace<void (*)(),tuple$<>>(void(*)() f) Line 125 (c:\rustc\fe5b13d681f25ee6474be29d748c65adcd91f69e\library\std\src\sys_common\backtrace.rs:125)
chess_ai.exe!std::rt::lang_start::closure$0<tuple$<>>(std::rt::lang_start::closure_env$0<tuple$<>> *) Line 145 (c:\rustc\fe5b13d681f25ee6474be29d748c65adcd91f69e\library\std\src\rt.rs:145)
[Inline Frame] chess_ai.exe!core::ops::function::impls::impl$2::call_once() Line 259 (c:\rustc\fe5b13d681f25ee6474be29d748c65adcd91f69e\library\core\src\ops\function.rs:259)

有没有办法找出是什么占据了堆栈中的空间?

在尝试使用gdb进行调试时(这显然完全启动了桶)(我也是,实际上对gdb缺乏经验):

代码语言:javascript
复制
GNU gdb (GDB) 8.1
Copyright (C) 2018 Free Software Foundation, Inc.
License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>
This is free software: you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law.  Type "show copying"
and "show warranty" for details.
This GDB was configured as "x86_64-w64-mingw32".
Type "show configuration" for configuration details.
For bug reporting instructions, please see:
<http://www.gnu.org/software/gdb/bugs/>.
Find the GDB manual and other documentation resources online at:
<http://www.gnu.org/software/gdb/documentation/>.
For help, type "help".
Type "apropos word" to search for commands related to "word"...
Reading symbols from .\target\debug\chess_ai.exe...(no debugging symbols found)...done.
(gdb) run
Starting program: C:\Users\elias\Documents\Projects\chess_ai\target\debug\chess_ai.exe 
[New Thread 29132.0x4d98]
[New Thread 29132.0x954]
[New Thread 29132.0x793c]
[New Thread 29132.0x603c]
Thread 1 received signal SIGSEGV, Segmentation fault.
0x00007ff69c048067 in ?? ()
(gdb) bt
#0  0x00007ff69c048067 in ?? ()
Backtrace stopped: previous frame identical to this frame (corrupt stack?)

实际上,这个程序在Linux上运行得非常好(崩溃发生在windows上)。有人告诉我,Linux上的堆栈要大得多。因此,如果有任何gdb技巧来查找大型变量,我可以在Linux上这样做。

EN

回答 1

Stack Overflow用户

发布于 2022-06-05 00:47:38

盒式数组基本上是一个大小固定的向量,但有一个警告:当您使用Box::new([...])创建它时,数组是在堆栈上创建的,然后通过Box::new()移动到堆中,而向量的元素数据则直接在堆上创建。如果您发现自己创建了像这个这样的大型装箱数组,那么您最好使用直接在堆上分配的vec![U64PerSquare::default(); 4096]。问题很可能是,您有多个嵌套级别的函数调用来创建这些装箱数组--或者说4096 * size_of::<U64PerSquare>()已经比堆栈大了。

如果您确实想要固定大小的类型,那么有一个三步进程可以使您在不需要堆栈分配的情况下到达那里:

如果盒式切片的长度与Vec<T>.

  • Convert不完全相等,则operation.

  • Convert

  • 会将其创建为Box<[T]>,这是一个对Box<[T; N]>来说是绝对正确的Box<[T]>

在你的例子中,看起来是这样的:

代码语言:javascript
复制
fn new_board() -> Box<[U64PerSquare; 4096]> {
    vec![Default::default(); 4096]
        .into_boxed_slice()
        .try_into()
        .unwrap()
}

您可以使用泛型来概括此模式:

代码语言:javascript
复制
fn new_boxed_array<T: Clone + Default, const N: usize>() -> Box<[T; N]> {
    vec![Default::default(); N]
        .into_boxed_slice()
        .try_into()
        // Mapping the error to a string prevents the requirement T:Debug,
        // and This Should Never Fail(TM) anyway.
        .map_err(|_| "conversion from slice to array failed")
        .unwrap()
}
票数 2
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/72503916

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档