33// GNU General Public License v3.0 or later
44// https://www.gnu.org/licenses/gpl-3.0-standalone.html
55
6- mod bench ;
6+ mod commands ;
77mod input_handler;
88mod perft;
99mod uci_handler;
1010
11- use crate :: uci_handler:: UciHandler ;
12- use chess:: definitions:: DEFAULT_FEN ;
11+ use crate :: {
12+ commands:: { bench:: BenchArgs , perft:: PerftArgs , split_perft:: SplitPerftArgs } ,
13+ uci_handler:: UciHandler ,
14+ } ;
15+
1316use clap:: { Parser , Subcommand } ;
1417use engine:: defs:: About ;
1518
@@ -28,39 +31,12 @@ struct Options {
2831#[ command( about = "Available commands" ) ]
2932enum Command {
3033 #[ command( about = "Run fixed depth search" ) ]
31- Bench {
32- #[ arg( short, long, default_value = "10" ) ]
33- depth : u8 ,
34-
35- #[ arg( short, long) ]
36- epd_file : Option < String > ,
37- } ,
38- Perft {
39- #[ arg( short, long, default_value_t = 6 ) ]
40- depth : usize ,
41- #[ arg(
42- short,
43- long,
44- default_value_t = DEFAULT_FEN . to_string( )
45- ) ]
46- fen : String ,
47- #[ arg( short, long) ]
48- epd_file : Option < String > ,
49- } ,
50- SplitPerft {
51- #[ arg( short, long, default_value_t = 6 ) ]
52- depth : usize ,
53- #[ arg(
54- short,
55- long,
56- default_value_t = DEFAULT_FEN . to_string( )
57- ) ]
58- fen : String ,
59- #[ arg( short, long, default_value_t = false ) ]
60- print_moves : bool ,
61- } ,
34+ Bench ( BenchArgs ) ,
35+ Perft ( PerftArgs ) ,
36+ SplitPerft ( SplitPerftArgs ) ,
6237}
6338
39+ /// Run the UCI handler for the engine.
6440fn run_uci ( ) {
6541 // Spawn UCI handler on a thread with 8 MiB stack — the search is deeply recursive
6642 // and the default main thread stack size is insufficient on some platforms.
@@ -82,53 +58,10 @@ fn main() {
8258 let args = Options :: parse ( ) ;
8359 match args. command {
8460 Some ( command) => match command {
85- Command :: Bench { depth, epd_file } => {
86- // Spawn bench on a thread with 8 MiB stack to match the UCI handler.
87- let handle = std:: thread:: Builder :: new ( )
88- . name ( "bench" . to_string ( ) )
89- . stack_size ( 8 * 1024 * 1024 )
90- . spawn ( move || bench:: bench ( depth, & epd_file) )
91- . unwrap ( ) ;
92- handle. join ( ) . unwrap ( ) ;
93- }
94- Command :: Perft {
95- depth,
96- fen,
97- epd_file,
98- } => {
99- let board = & mut chess:: board:: Board :: from_fen ( & fen) . unwrap ( ) ;
100- if let Some ( epd) = epd_file {
101- perft:: process_epd_file ( & epd) ;
102- } else {
103- for i in 1 ..depth + 1 {
104- let now = std:: time:: Instant :: now ( ) ;
105- let nodes = chess:: perft:: perft ( board, i, false ) . unwrap ( ) ;
106- let elapsed = now. elapsed ( ) ;
107- let nps = nodes as f64 / elapsed. as_secs_f64 ( ) ;
108- println ! (
109- "perft {} = {:>12} {:.2} sec {:>12} nps" ,
110- i,
111- nodes,
112- elapsed. as_secs_f64( ) ,
113- nps. round( )
114- ) ;
115- }
116- }
117- }
118- Command :: SplitPerft {
119- depth,
120- fen,
121- print_moves,
122- } => {
123- println ! ( "running split perft at depth {}" , depth) ;
124- let board = & mut chess:: board:: Board :: from_fen ( & fen) . unwrap ( ) ;
125- let move_results = chess:: perft:: split_perft ( board, depth, print_moves) . unwrap ( ) ;
126- for res in & move_results {
127- println ! ( "{}: {}" , res. mv. to_long_algebraic( ) , res. nodes) ;
128- }
129- println ! ( ) ;
130- // print the total nodes
131- println ! ( "{}" , move_results. iter( ) . map( |r| r. nodes) . sum:: <u64 >( ) ) ;
61+ Command :: Bench ( bench_args) => commands:: bench:: execute ( bench_args) ,
62+ Command :: Perft ( perft_args) => commands:: perft:: execute ( perft_args) ,
63+ Command :: SplitPerft ( split_perft_args) => {
64+ commands:: split_perft:: execute ( split_perft_args)
13265 }
13366 } ,
13467 None => run_uci ( ) ,
0 commit comments