From 3d271049a6ed311ad1bf9ff5f6478e817a743c22 Mon Sep 17 00:00:00 2001 From: borg323 Date: Tue, 17 Aug 2021 01:37:15 +0300 Subject: [PATCH 01/10] allow option idientifiers that start with a digit --- src/utils/optionsdict.cc | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/src/utils/optionsdict.cc b/src/utils/optionsdict.cc index b515914c36..624b33e3ea 100644 --- a/src/utils/optionsdict.cc +++ b/src/utils/optionsdict.cc @@ -124,6 +124,13 @@ class Lexer { static const std::string kNumberChars = "0123456789-."; if (kNumberChars.find(str_[idx_]) != std::string::npos) { ReadNumber(); + // If the next character isn't a separator, this is probably an identifier + // starting with a digit. + if (idx_ != str_.size() && !std::isspace(str_[idx_]) && + str_[idx_] != ',' && str_[idx_] != ')') { + idx_ = last_offset_; + ReadIdentifier(); + } return; } From 4ee9fb0cb2707066dd0ceb6ca7e81f218fc54cb0 Mon Sep 17 00:00:00 2001 From: borg323 Date: Sat, 2 Mar 2024 15:10:20 +0200 Subject: [PATCH 02/10] switch backend --- meson.build | 1 + src/neural/network_blend.cc | 169 +++++++++++++++++++++++++++++++++++ src/neural/network_switch.cc | 152 +++++++++++++++++++++++++++++++ 3 files changed, 322 insertions(+) create mode 100644 src/neural/network_blend.cc create mode 100644 src/neural/network_switch.cc diff --git a/meson.build b/meson.build index 7eb9e7b937..340fc4d26a 100644 --- a/meson.build +++ b/meson.build @@ -204,6 +204,7 @@ files += [ 'src/neural/network_random.cc', 'src/neural/network_record.cc', 'src/neural/network_rr.cc', + 'src/neural/network_switch.cc', 'src/neural/network_trivial.cc', 'src/neural/onnx/adapters.cc', 'src/neural/onnx/builder.cc', diff --git a/src/neural/network_blend.cc b/src/neural/network_blend.cc new file mode 100644 index 0000000000..b6921183ca --- /dev/null +++ b/src/neural/network_blend.cc @@ -0,0 +1,169 @@ +/* + This file is part of Leela Chess Zero. + Copyright (C) 2018-2021 The LCZero Authors + + Leela Chess is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + Leela Chess is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with Leela Chess. If not, see . + + Additional permission under GNU GPL version 3 section 7 + + If you modify this Program, or any covered work, by linking or + combining it with NVIDIA Corporation's libraries from the NVIDIA CUDA + Toolkit and the NVIDIA CUDA Deep Neural Network library (or a + modified version of those libraries), containing parts covered by the + terms of the respective license agreement, the licensors of this + Program grant you additional permission to convey the resulting work. + */ + +#include "neural/factory.h" +#include "neural/network.h" +#include "utils/logging.h" + +namespace lczero { + +namespace { + +class BlendNetwork; + +class BlendComputation : public NetworkComputation { + public: + BlendComputation(std::unique_ptr work_comp, + std::unique_ptr policy_comp) + : work_comp_(std::move(work_comp)), + policy_comp_(std::move(policy_comp)) {} + + void AddInput(InputPlanes&& input) override { + InputPlanes x = input; + InputPlanes y = input; + work_comp_->AddInput(std::move(x)); + policy_comp_->AddInput(std::move(y)); + } + + void ComputeBlocking() override { + work_comp_->ComputeBlocking(); + policy_comp_->ComputeBlocking(); + } + + int GetBatchSize() const override { + return static_cast(work_comp_->GetBatchSize()); + } + + float GetQVal(int sample) const override { + return work_comp_->GetQVal(sample); + } + + float GetDVal(int sample) const override { + return work_comp_->GetDVal(sample); + } + + float GetMVal(int sample) const override { + return work_comp_->GetMVal(sample); + } + + float GetPVal(int sample, int move_id) const override { + return policy_comp_->GetPVal(sample, move_id); + } + + private: + std::unique_ptr work_comp_; + std::unique_ptr policy_comp_; +}; + +class BlendNetwork : public Network { + public: + BlendNetwork(const std::optional& weights, + const OptionsDict& options) { + auto backends = NetworkFactory::Get()->GetBackendsList(); + + OptionsDict dict1; + std::string backendName1 = backends[0]; + OptionsDict& backend1_dict = dict1; + std::string networkName1 = ""; + + OptionsDict dict2; + std::string backendName2 = backends[0]; + OptionsDict& backend2_dict = dict2; + std::string networkName2 = ""; + + const auto parents = options.ListSubdicts(); + + if (parents.size() == 0) { + backendName1 = options.GetOrDefault("backend", backendName1); + networkName1 = options.GetOrDefault("weights", networkName1); + } else { + backend1_dict = options.GetSubdict(parents[0]); + backendName1 = + backend1_dict.GetOrDefault("backend", backendName1); + networkName1 = + backend1_dict.GetOrDefault("weights", networkName1); + } + if (parents.size() > 1) { + backend2_dict = options.GetSubdict(parents[1]); + backendName2 = + backend2_dict.GetOrDefault("backend", backendName2); + networkName2 = + backend2_dict.GetOrDefault("weights", networkName2); + } + if (parents.size() > 2) { + CERR << "Warning, cannot blend more than two backends"; + } + + if (networkName1 == "") { + policy_net_ = + NetworkFactory::Get()->Create(backendName1, weights, backend1_dict); + } else { + CERR << "Policy net set to " << networkName1 << "."; + std::optional weights1; + weights1 = LoadWeightsFromFile(networkName1); + policy_net_ = + NetworkFactory::Get()->Create(backendName1, weights1, backend1_dict); + } + + if (networkName2 == "") { + work_net_ = + NetworkFactory::Get()->Create(backendName2, weights, backend2_dict); + } else { + CERR << "Working net set to " << networkName2 << "."; + std::optional weights2; + weights2 = LoadWeightsFromFile(networkName2); + work_net_ = + NetworkFactory::Get()->Create(backendName2, weights2, backend2_dict); + } + } + + std::unique_ptr NewComputation() override { + std::unique_ptr work_comp = work_net_->NewComputation(); + std::unique_ptr policy_comp = + policy_net_->NewComputation(); + return std::make_unique(std::move(work_comp), + std::move(policy_comp)); + } + + const NetworkCapabilities& GetCapabilities() const override { + return work_net_->GetCapabilities(); + } + + private: + std::unique_ptr work_net_; + std::unique_ptr policy_net_; +}; + +std::unique_ptr MakeBlendNetwork( + const std::optional& weights, const OptionsDict& options) { + return std::make_unique(weights, options); +} + +REGISTER_NETWORK("blend", MakeBlendNetwork, -800) + +} // namespace +} // namespace lczero diff --git a/src/neural/network_switch.cc b/src/neural/network_switch.cc new file mode 100644 index 0000000000..45e054681d --- /dev/null +++ b/src/neural/network_switch.cc @@ -0,0 +1,152 @@ +/* + This file is part of Leela Chess Zero. + Copyright (C) 2024 The LCZero Authors + + Leela Chess is free software: you can redistribute it and/or modify + it under the terms of the GNU General Public License as published by + the Free Software Foundation, either version 3 of the License, or + (at your option) any later version. + + Leela Chess is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + GNU General Public License for more details. + + You should have received a copy of the GNU General Public License + along with Leela Chess. If not, see . + + Additional permission under GNU GPL version 3 section 7 + + If you modify this Program, or any covered work, by linking or + combining it with NVIDIA Corporation's libraries from the NVIDIA CUDA + Toolkit and the NVIDIA CUDA Deep Neural Network library (or a + modified version of those libraries), containing parts covered by the + terms of the respective license agreement, the licensors of this + Program grant you additional permission to convey the resulting work. + */ + +#include "neural/network.h" +#include "chess/bitboard.h" +#include "neural/factory.h" +#include "utils/logging.h" + +namespace lczero { + +namespace { + +class SwitchNetwork; + +class SwitchComputation : public NetworkComputation { + public: + SwitchComputation(std::unique_ptr main_comp, + std::unique_ptr endgame_comp) + : main_comp_(std::move(main_comp)), + endgame_comp_(std::move(endgame_comp)) {} + + void AddInput(InputPlanes&& input) override { + auto pieces = input[1].mask | input[2].mask | input[3].mask | + input[4].mask | input[7].mask | input[8].mask | + input[9].mask | input[10].mask; + if (BitBoard(pieces).count() > 6) { + is_endgame_.push_back(false); + rev_idx_.push_back(main_idx_.size()); + main_idx_.push_back(main_idx_.size()); + main_comp_->AddInput(std::move(input)); + } else { + is_endgame_.push_back(true); + rev_idx_.push_back(endgame_idx_.size()); + endgame_idx_.push_back(endgame_idx_.size()); + endgame_comp_->AddInput(std::move(input)); + } + } + + void ComputeBlocking() override { + if (main_idx_.size() > 0) main_comp_->ComputeBlocking(); + if (endgame_idx_.size() > 0) endgame_comp_->ComputeBlocking(); + } + + int GetBatchSize() const override { + return static_cast(main_comp_->GetBatchSize() + + endgame_comp_->GetBatchSize()); + } + + float GetQVal(int sample) const override { + if (is_endgame_[sample]) { + return endgame_comp_->GetQVal(rev_idx_[sample]); + } + return main_comp_->GetQVal(rev_idx_[sample]); + } + + float GetDVal(int sample) const override { + if (is_endgame_[sample]) { + return endgame_comp_->GetDVal(rev_idx_[sample]); + } + return main_comp_->GetDVal(rev_idx_[sample]); + } + + float GetMVal(int sample) const override { + if (is_endgame_[sample]) { + return endgame_comp_->GetMVal(rev_idx_[sample]); + } + return main_comp_->GetMVal(rev_idx_[sample]); + } + + float GetPVal(int sample, int move_id) const override { + if (is_endgame_[sample]) { + return endgame_comp_->GetPVal(rev_idx_[sample], move_id); + } + return main_comp_->GetPVal(rev_idx_[sample], move_id); + } + + private: + std::unique_ptr main_comp_; + std::unique_ptr endgame_comp_; + std::vector main_idx_; + std::vector endgame_idx_; + std::vector rev_idx_; + std::vector is_endgame_; +}; + +class SwitchNetwork : public Network { + public: + SwitchNetwork(const std::optional& weights, + const OptionsDict& options) { + auto backends = NetworkFactory::Get()->GetBackendsList(); + auto backend = options.GetOrDefault("backend", backends[0]); + auto endgame_net = options.Get("endgame_weights"); + + main_net_ = NetworkFactory::Get()->Create(backend, weights, options); + + CERR << "Loading ensgame weights file from: " << endgame_net; + std::optional endgame_weights = + LoadWeightsFromFile(endgame_net); + endgame_net_ = + NetworkFactory::Get()->Create(backend, endgame_weights, options); + } + + std::unique_ptr NewComputation() override { + std::unique_ptr main_comp = main_net_->NewComputation(); + std::unique_ptr endgame_comp = + endgame_net_->NewComputation(); + return std::make_unique(std::move(main_comp), + std::move(endgame_comp)); + } + + const NetworkCapabilities& GetCapabilities() const override { + return main_net_->GetCapabilities(); + } + + private: + std::unique_ptr main_net_; + std::unique_ptr endgame_net_; +}; + +std::unique_ptr MakeSwitchNetwork( + const std::optional& weights, const OptionsDict& options) { + return std::make_unique(weights, options); +} + +REGISTER_NETWORK("switch", MakeSwitchNetwork, -800) + +} // namespace +} // namespace lczero From 313738a6b7bf0267321d74df331cdecc72b1621a Mon Sep 17 00:00:00 2001 From: borg323 Date: Wed, 6 Mar 2024 01:19:41 +0200 Subject: [PATCH 03/10] add threads option --- src/neural/network_switch.cc | 29 ++++++++++++++++++++++------- 1 file changed, 22 insertions(+), 7 deletions(-) diff --git a/src/neural/network_switch.cc b/src/neural/network_switch.cc index 45e054681d..241b127bbb 100644 --- a/src/neural/network_switch.cc +++ b/src/neural/network_switch.cc @@ -25,9 +25,11 @@ Program grant you additional permission to convey the resulting work. */ -#include "neural/network.h" +#include + #include "chess/bitboard.h" #include "neural/factory.h" +#include "neural/network.h" #include "utils/logging.h" namespace lczero { @@ -39,9 +41,11 @@ class SwitchNetwork; class SwitchComputation : public NetworkComputation { public: SwitchComputation(std::unique_ptr main_comp, - std::unique_ptr endgame_comp) + std::unique_ptr endgame_comp, + int threads) : main_comp_(std::move(main_comp)), - endgame_comp_(std::move(endgame_comp)) {} + endgame_comp_(std::move(endgame_comp)), + threads_(threads) {} void AddInput(InputPlanes&& input) override { auto pieces = input[1].mask | input[2].mask | input[3].mask | @@ -61,8 +65,16 @@ class SwitchComputation : public NetworkComputation { } void ComputeBlocking() override { - if (main_idx_.size() > 0) main_comp_->ComputeBlocking(); - if (endgame_idx_.size() > 0) endgame_comp_->ComputeBlocking(); + if (threads_ > 1 && main_idx_.size() > 0 && endgame_idx_.size() > 0) { + std::thread main( + [](NetworkComputation* comp) { comp->ComputeBlocking(); }, + main_comp_.get()); + endgame_comp_->ComputeBlocking(); + main.join(); + } else { + if (main_idx_.size() > 0) main_comp_->ComputeBlocking(); + if (endgame_idx_.size() > 0) endgame_comp_->ComputeBlocking(); + } } int GetBatchSize() const override { @@ -105,6 +117,7 @@ class SwitchComputation : public NetworkComputation { std::vector endgame_idx_; std::vector rev_idx_; std::vector is_endgame_; + int threads_; }; class SwitchNetwork : public Network { @@ -114,6 +127,7 @@ class SwitchNetwork : public Network { auto backends = NetworkFactory::Get()->GetBackendsList(); auto backend = options.GetOrDefault("backend", backends[0]); auto endgame_net = options.Get("endgame_weights"); + threads_ = options.GetOrDefault("threads", 1); main_net_ = NetworkFactory::Get()->Create(backend, weights, options); @@ -128,8 +142,8 @@ class SwitchNetwork : public Network { std::unique_ptr main_comp = main_net_->NewComputation(); std::unique_ptr endgame_comp = endgame_net_->NewComputation(); - return std::make_unique(std::move(main_comp), - std::move(endgame_comp)); + return std::make_unique( + std::move(main_comp), std::move(endgame_comp), threads_); } const NetworkCapabilities& GetCapabilities() const override { @@ -139,6 +153,7 @@ class SwitchNetwork : public Network { private: std::unique_ptr main_net_; std::unique_ptr endgame_net_; + int threads_; }; std::unique_ptr MakeSwitchNetwork( From 079fad8ad7d9fe03d1d371788d680bf9df7beea0 Mon Sep 17 00:00:00 2001 From: borg323 Date: Wed, 6 Mar 2024 01:44:52 +0200 Subject: [PATCH 04/10] add missing overrides --- src/neural/network_switch.cc | 20 +++++++++++++++++++- 1 file changed, 19 insertions(+), 1 deletion(-) diff --git a/src/neural/network_switch.cc b/src/neural/network_switch.cc index 241b127bbb..c4f6f3e195 100644 --- a/src/neural/network_switch.cc +++ b/src/neural/network_switch.cc @@ -136,6 +136,9 @@ class SwitchNetwork : public Network { LoadWeightsFromFile(endgame_net); endgame_net_ = NetworkFactory::Get()->Create(backend, endgame_weights, options); + + capabilities_ = main_net_->GetCapabilities(); + capabilities_.Merge(endgame_net_->GetCapabilities()); } std::unique_ptr NewComputation() override { @@ -147,13 +150,28 @@ class SwitchNetwork : public Network { } const NetworkCapabilities& GetCapabilities() const override { - return main_net_->GetCapabilities(); + return capabilities_; + } + + int GetMiniBatchSize() const override { + return std::min(main_net_->GetMiniBatchSize(), + endgame_net_->GetMiniBatchSize()); + } + + bool IsCpu() const override { + return main_net_->GetMiniBatchSize() | endgame_net_->GetMiniBatchSize(); + } + + void InitThread(int id) override { + main_net_->InitThread(id); + endgame_net_->InitThread(id); } private: std::unique_ptr main_net_; std::unique_ptr endgame_net_; int threads_; + NetworkCapabilities capabilities_; }; std::unique_ptr MakeSwitchNetwork( From f5ca7f739545d9079638896125526ab5cacbe08b Mon Sep 17 00:00:00 2001 From: borg323 Date: Wed, 6 Mar 2024 18:25:50 +0200 Subject: [PATCH 05/10] fix blas threading issues --- src/neural/blas/network_blas.cc | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-) diff --git a/src/neural/blas/network_blas.cc b/src/neural/blas/network_blas.cc index a212ce931e..b08f47d731 100644 --- a/src/neural/blas/network_blas.cc +++ b/src/neural/blas/network_blas.cc @@ -228,11 +228,7 @@ BlasComputation::BlasComputation( ffn_activation_(ffn_activation), attn_policy_(attn_policy), attn_body_(attn_body), - network_(network) { -#ifdef USE_DNNL - omp_set_num_threads(1); -#endif -} + network_(network) { } template using EigenMatrixMap = @@ -457,6 +453,9 @@ void BlasComputation::MakeEncoderLayer( template void BlasComputation::ComputeBlocking() { +#ifdef USE_DNNL + if (!use_eigen) omp_set_num_threads(1); +#endif const auto& value_head = weights_.value_heads.at("winner"); const auto& policy_head = weights_.policy_heads.at("vanilla"); // Retrieve network key dimensions from the weights structure. @@ -967,6 +966,7 @@ BlasNetwork::BlasNetwork(const WeightsFile& file, } if (use_eigen) { + Eigen::setNbThreads(1); CERR << "Using Eigen version " << EIGEN_WORLD_VERSION << "." << EIGEN_MAJOR_VERSION << "." << EIGEN_MINOR_VERSION; CERR << "Eigen max batch size is " << max_batch_size_ << "."; From 8ac4cd254f0c9abade2236932107d9c25cfa73b4 Mon Sep 17 00:00:00 2001 From: borg323 Date: Wed, 6 Mar 2024 18:36:41 +0200 Subject: [PATCH 06/10] allow backend configuration --- src/neural/network_switch.cc | 20 +++++++++++++++----- 1 file changed, 15 insertions(+), 5 deletions(-) diff --git a/src/neural/network_switch.cc b/src/neural/network_switch.cc index c4f6f3e195..0f971ad130 100644 --- a/src/neural/network_switch.cc +++ b/src/neural/network_switch.cc @@ -125,17 +125,27 @@ class SwitchNetwork : public Network { SwitchNetwork(const std::optional& weights, const OptionsDict& options) { auto backends = NetworkFactory::Get()->GetBackendsList(); - auto backend = options.GetOrDefault("backend", backends[0]); + auto endgame_net = options.Get("endgame_weights"); threads_ = options.GetOrDefault("threads", 1); - main_net_ = NetworkFactory::Get()->Create(backend, weights, options); + auto& main_options = + options.HasSubdict("main") ? options.GetSubdict("main") : options; + + main_net_ = NetworkFactory::Get()->Create( + main_options.GetOrDefault("backend", backends[0]), weights, + main_options); - CERR << "Loading ensgame weights file from: " << endgame_net; + CERR << "Loading endgame weights file from: " << endgame_net; std::optional endgame_weights = LoadWeightsFromFile(endgame_net); - endgame_net_ = - NetworkFactory::Get()->Create(backend, endgame_weights, options); + + auto& endgame_options = + options.HasSubdict("endgame") ? options.GetSubdict("endgame") : options; + + endgame_net_ = NetworkFactory::Get()->Create( + endgame_options.GetOrDefault("backend", backends[0]), + endgame_weights, endgame_options); capabilities_ = main_net_->GetCapabilities(); capabilities_.Merge(endgame_net_->GetCapabilities()); From 3bf309114c067660998a85c9b1b2b0a7b27a27ff Mon Sep 17 00:00:00 2001 From: borg323 Date: Wed, 6 Mar 2024 18:51:34 +0200 Subject: [PATCH 07/10] make endgame_weights optional --- src/neural/network_switch.cc | 12 +++++++----- 1 file changed, 7 insertions(+), 5 deletions(-) diff --git a/src/neural/network_switch.cc b/src/neural/network_switch.cc index 0f971ad130..6a14c74498 100644 --- a/src/neural/network_switch.cc +++ b/src/neural/network_switch.cc @@ -126,7 +126,6 @@ class SwitchNetwork : public Network { const OptionsDict& options) { auto backends = NetworkFactory::Get()->GetBackendsList(); - auto endgame_net = options.Get("endgame_weights"); threads_ = options.GetOrDefault("threads", 1); auto& main_options = @@ -136,16 +135,19 @@ class SwitchNetwork : public Network { main_options.GetOrDefault("backend", backends[0]), weights, main_options); - CERR << "Loading endgame weights file from: " << endgame_net; - std::optional endgame_weights = - LoadWeightsFromFile(endgame_net); + std::optional endgame_weights; + if (!options.IsDefault("endgame_weights")) { + auto name = options.Get("endgame_weights"); + CERR << "Loading endgame weights file from: " << name; + endgame_weights = LoadWeightsFromFile(name); + } auto& endgame_options = options.HasSubdict("endgame") ? options.GetSubdict("endgame") : options; endgame_net_ = NetworkFactory::Get()->Create( endgame_options.GetOrDefault("backend", backends[0]), - endgame_weights, endgame_options); + endgame_weights ? endgame_weights : weights, endgame_options); capabilities_ = main_net_->GetCapabilities(); capabilities_.Merge(endgame_net_->GetCapabilities()); From 81dd539053cfe43047511184a6041811a0c6705b Mon Sep 17 00:00:00 2001 From: borg323 Date: Wed, 6 Mar 2024 22:07:20 +0200 Subject: [PATCH 08/10] configurable threshold --- src/neural/network_switch.cc | 10 +++++++--- 1 file changed, 7 insertions(+), 3 deletions(-) diff --git a/src/neural/network_switch.cc b/src/neural/network_switch.cc index 6a14c74498..cfc5eddc8c 100644 --- a/src/neural/network_switch.cc +++ b/src/neural/network_switch.cc @@ -42,16 +42,17 @@ class SwitchComputation : public NetworkComputation { public: SwitchComputation(std::unique_ptr main_comp, std::unique_ptr endgame_comp, - int threads) + int threshold, int threads) : main_comp_(std::move(main_comp)), endgame_comp_(std::move(endgame_comp)), + threshold_(threshold), threads_(threads) {} void AddInput(InputPlanes&& input) override { auto pieces = input[1].mask | input[2].mask | input[3].mask | input[4].mask | input[7].mask | input[8].mask | input[9].mask | input[10].mask; - if (BitBoard(pieces).count() > 6) { + if (BitBoard(pieces).count() > threshold_) { is_endgame_.push_back(false); rev_idx_.push_back(main_idx_.size()); main_idx_.push_back(main_idx_.size()); @@ -117,6 +118,7 @@ class SwitchComputation : public NetworkComputation { std::vector endgame_idx_; std::vector rev_idx_; std::vector is_endgame_; + int threshold_; int threads_; }; @@ -126,6 +128,7 @@ class SwitchNetwork : public Network { const OptionsDict& options) { auto backends = NetworkFactory::Get()->GetBackendsList(); + threshold_ = options.GetOrDefault("threshold", 6); threads_ = options.GetOrDefault("threads", 1); auto& main_options = @@ -158,7 +161,7 @@ class SwitchNetwork : public Network { std::unique_ptr endgame_comp = endgame_net_->NewComputation(); return std::make_unique( - std::move(main_comp), std::move(endgame_comp), threads_); + std::move(main_comp), std::move(endgame_comp), threshold_, threads_); } const NetworkCapabilities& GetCapabilities() const override { @@ -182,6 +185,7 @@ class SwitchNetwork : public Network { private: std::unique_ptr main_net_; std::unique_ptr endgame_net_; + int threshold_; int threads_; NetworkCapabilities capabilities_; }; From 76b28fbf61d0648da2b8635f910582d2ff491168 Mon Sep 17 00:00:00 2001 From: borg323 Date: Wed, 6 Mar 2024 22:16:53 +0200 Subject: [PATCH 09/10] simplify --- src/neural/network_switch.cc | 23 ++++++++++------------- 1 file changed, 10 insertions(+), 13 deletions(-) diff --git a/src/neural/network_switch.cc b/src/neural/network_switch.cc index cfc5eddc8c..5b016a3e08 100644 --- a/src/neural/network_switch.cc +++ b/src/neural/network_switch.cc @@ -54,34 +54,31 @@ class SwitchComputation : public NetworkComputation { input[9].mask | input[10].mask; if (BitBoard(pieces).count() > threshold_) { is_endgame_.push_back(false); - rev_idx_.push_back(main_idx_.size()); - main_idx_.push_back(main_idx_.size()); + rev_idx_.push_back(main_cnt_); + main_cnt_++; main_comp_->AddInput(std::move(input)); } else { is_endgame_.push_back(true); - rev_idx_.push_back(endgame_idx_.size()); - endgame_idx_.push_back(endgame_idx_.size()); + rev_idx_.push_back(endgame_cnt_); + endgame_cnt_++; endgame_comp_->AddInput(std::move(input)); } } void ComputeBlocking() override { - if (threads_ > 1 && main_idx_.size() > 0 && endgame_idx_.size() > 0) { + if (threads_ > 1 && main_cnt_ > 0 && endgame_cnt_ > 0) { std::thread main( [](NetworkComputation* comp) { comp->ComputeBlocking(); }, main_comp_.get()); endgame_comp_->ComputeBlocking(); main.join(); } else { - if (main_idx_.size() > 0) main_comp_->ComputeBlocking(); - if (endgame_idx_.size() > 0) endgame_comp_->ComputeBlocking(); + if (main_cnt_ > 0) main_comp_->ComputeBlocking(); + if (endgame_cnt_ > 0) endgame_comp_->ComputeBlocking(); } } - int GetBatchSize() const override { - return static_cast(main_comp_->GetBatchSize() + - endgame_comp_->GetBatchSize()); - } + int GetBatchSize() const override { return main_cnt_ + endgame_cnt_; } float GetQVal(int sample) const override { if (is_endgame_[sample]) { @@ -114,8 +111,8 @@ class SwitchComputation : public NetworkComputation { private: std::unique_ptr main_comp_; std::unique_ptr endgame_comp_; - std::vector main_idx_; - std::vector endgame_idx_; + int main_cnt_ = 0; + int endgame_cnt_ = 0; std::vector rev_idx_; std::vector is_endgame_; int threshold_; From 1404ff37dbe26434d0880e07781dda21a1c04a20 Mon Sep 17 00:00:00 2001 From: borg323 Date: Fri, 15 Mar 2024 18:45:34 +0200 Subject: [PATCH 10/10] remove unrelated code --- src/neural/network_blend.cc | 169 ------------------------------------ 1 file changed, 169 deletions(-) delete mode 100644 src/neural/network_blend.cc diff --git a/src/neural/network_blend.cc b/src/neural/network_blend.cc deleted file mode 100644 index b6921183ca..0000000000 --- a/src/neural/network_blend.cc +++ /dev/null @@ -1,169 +0,0 @@ -/* - This file is part of Leela Chess Zero. - Copyright (C) 2018-2021 The LCZero Authors - - Leela Chess is free software: you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation, either version 3 of the License, or - (at your option) any later version. - - Leela Chess is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with Leela Chess. If not, see . - - Additional permission under GNU GPL version 3 section 7 - - If you modify this Program, or any covered work, by linking or - combining it with NVIDIA Corporation's libraries from the NVIDIA CUDA - Toolkit and the NVIDIA CUDA Deep Neural Network library (or a - modified version of those libraries), containing parts covered by the - terms of the respective license agreement, the licensors of this - Program grant you additional permission to convey the resulting work. - */ - -#include "neural/factory.h" -#include "neural/network.h" -#include "utils/logging.h" - -namespace lczero { - -namespace { - -class BlendNetwork; - -class BlendComputation : public NetworkComputation { - public: - BlendComputation(std::unique_ptr work_comp, - std::unique_ptr policy_comp) - : work_comp_(std::move(work_comp)), - policy_comp_(std::move(policy_comp)) {} - - void AddInput(InputPlanes&& input) override { - InputPlanes x = input; - InputPlanes y = input; - work_comp_->AddInput(std::move(x)); - policy_comp_->AddInput(std::move(y)); - } - - void ComputeBlocking() override { - work_comp_->ComputeBlocking(); - policy_comp_->ComputeBlocking(); - } - - int GetBatchSize() const override { - return static_cast(work_comp_->GetBatchSize()); - } - - float GetQVal(int sample) const override { - return work_comp_->GetQVal(sample); - } - - float GetDVal(int sample) const override { - return work_comp_->GetDVal(sample); - } - - float GetMVal(int sample) const override { - return work_comp_->GetMVal(sample); - } - - float GetPVal(int sample, int move_id) const override { - return policy_comp_->GetPVal(sample, move_id); - } - - private: - std::unique_ptr work_comp_; - std::unique_ptr policy_comp_; -}; - -class BlendNetwork : public Network { - public: - BlendNetwork(const std::optional& weights, - const OptionsDict& options) { - auto backends = NetworkFactory::Get()->GetBackendsList(); - - OptionsDict dict1; - std::string backendName1 = backends[0]; - OptionsDict& backend1_dict = dict1; - std::string networkName1 = ""; - - OptionsDict dict2; - std::string backendName2 = backends[0]; - OptionsDict& backend2_dict = dict2; - std::string networkName2 = ""; - - const auto parents = options.ListSubdicts(); - - if (parents.size() == 0) { - backendName1 = options.GetOrDefault("backend", backendName1); - networkName1 = options.GetOrDefault("weights", networkName1); - } else { - backend1_dict = options.GetSubdict(parents[0]); - backendName1 = - backend1_dict.GetOrDefault("backend", backendName1); - networkName1 = - backend1_dict.GetOrDefault("weights", networkName1); - } - if (parents.size() > 1) { - backend2_dict = options.GetSubdict(parents[1]); - backendName2 = - backend2_dict.GetOrDefault("backend", backendName2); - networkName2 = - backend2_dict.GetOrDefault("weights", networkName2); - } - if (parents.size() > 2) { - CERR << "Warning, cannot blend more than two backends"; - } - - if (networkName1 == "") { - policy_net_ = - NetworkFactory::Get()->Create(backendName1, weights, backend1_dict); - } else { - CERR << "Policy net set to " << networkName1 << "."; - std::optional weights1; - weights1 = LoadWeightsFromFile(networkName1); - policy_net_ = - NetworkFactory::Get()->Create(backendName1, weights1, backend1_dict); - } - - if (networkName2 == "") { - work_net_ = - NetworkFactory::Get()->Create(backendName2, weights, backend2_dict); - } else { - CERR << "Working net set to " << networkName2 << "."; - std::optional weights2; - weights2 = LoadWeightsFromFile(networkName2); - work_net_ = - NetworkFactory::Get()->Create(backendName2, weights2, backend2_dict); - } - } - - std::unique_ptr NewComputation() override { - std::unique_ptr work_comp = work_net_->NewComputation(); - std::unique_ptr policy_comp = - policy_net_->NewComputation(); - return std::make_unique(std::move(work_comp), - std::move(policy_comp)); - } - - const NetworkCapabilities& GetCapabilities() const override { - return work_net_->GetCapabilities(); - } - - private: - std::unique_ptr work_net_; - std::unique_ptr policy_net_; -}; - -std::unique_ptr MakeBlendNetwork( - const std::optional& weights, const OptionsDict& options) { - return std::make_unique(weights, options); -} - -REGISTER_NETWORK("blend", MakeBlendNetwork, -800) - -} // namespace -} // namespace lczero