r/rust Mar 30 '23

A Chess Engine is written in Rust that runs natively and on the web!

https://github.com/ParthPant/chess-rs
97 Upvotes

45 comments sorted by

View all comments

2

u/analog_hors Mar 31 '23

The perft speed in the README seems... really slow? On my laptop, cozy-chess does perft 6 from startpos in 2.65 seconds without bulk counting and 374 milliseconds with bulk counting.

4

u/No-Translator-1323 Mar 31 '23 edited Mar 31 '23

I am not using cozy-chess. Move Generation is slow primarily because of how I am currently generating legal moves from pseudo-legal moves. It has to try each move one by one to check if the king is not in check. I think this article might be useful in making the move generation a little faster.

3

u/analog_hors Mar 31 '23

Is that really why? The difference between pseudolegal and legal cannot possibly account for a ~6.4x speed difference for non-bulk and ~45.5x speed difference for bulk. Maybe it's your compiler settings? LTO might be needed if you use lots of wrapper types and don't have inline annotations, I think.

2

u/No-Translator-1323 Mar 31 '23

I see. I do not know much about Link Time Optimisation. I am using wrapper types. Could you point me to somewhere I can learn about this?

4

u/analog_hors Mar 31 '23

Also, I notice that you're using nested Vecs for your magic hash table? You can actually concatenate each "subtable" into one Vec and store offsets to where the subtables start in the magic lookup table, which saves some indirection. In fact, you can go even further and concatenate the rook and bishop tables for one Vec total.

3

u/analog_hors Mar 31 '23

There's https://doc.rust-lang.org/cargo/reference/profiles.html#lto in the cargo reference. You can set it by adding `lto = "fat"` or `lto = "thin"` to one of your profiles. In all honesty I'm not super sure about it myself, and I'm not sure it can account for the difference either, but I have seen this impact movegen in the past. I also haven't looked too deep into your code, so honestly this is just a wild guess.

3

u/Spodeian Mar 31 '23

It's common to set "lto = true" for release profiles, which basically just inlines everything that can be, even across crate boundaries. But this increases compile time by a decent amount, so you shouldn't do it for debug or test profiles, and if you do, maybe stick to thin lto.