From ad852aeaea8e77e97e971131ab67d2fc07bfe4fa Mon Sep 17 00:00:00 2001 From: Eduard Valeyev Date: Tue, 15 Jun 2021 22:15:26 -0400 Subject: [PATCH] DistArray::set can properly avoid copies (unless setting remote data) when given rvalue ref --- INSTALL.md | 2 +- external/versions.cmake | 4 ++-- src/TiledArray/distributed_storage.h | 31 +++++++++++++++++++++++----- 3 files changed, 29 insertions(+), 8 deletions(-) diff --git a/INSTALL.md b/INSTALL.md index 8268d75dc8..f2dc253661 100644 --- a/INSTALL.md +++ b/INSTALL.md @@ -42,7 +42,7 @@ Both methods are supported. However, for most users we _strongly_ recommend to b - Boost.Range: header-only, *only used for unit testing* - [BTAS](http://github.com/ValeevGroup/BTAS), tag d7794799e4510cf66844081dd8f1f5b648112d33 . If usable BTAS installation is not found, TiledArray will download and compile BTAS from source. *This is the recommended way to compile BTAS for all users*. - - [MADNESS](https://github.com/m-a-d-n-e-s-s/madness), tag b378fd6f1fcadf1cd1ce4541ca4100c335b874ee . +- [MADNESS](https://github.com/m-a-d-n-e-s-s/madness), tag 7ce06234c23aa8e0ab3d9e9b87eff9cd85390d80 . Only the MADworld runtime and BLAS/LAPACK C API component of MADNESS is used by TiledArray. If usable MADNESS installation is not found, TiledArray will download and compile MADNESS from source. *This is the recommended way to compile MADNESS for all users*. diff --git a/external/versions.cmake b/external/versions.cmake index d91772d911..6ebeb1aa32 100644 --- a/external/versions.cmake +++ b/external/versions.cmake @@ -19,8 +19,8 @@ set(TA_INSTALL_EIGEN_PREVIOUS_VERSION 3.3.7) set(TA_INSTALL_EIGEN_URL_HASH b9e98a200d2455f06db9c661c5610496) set(TA_INSTALL_EIGEN_PREVIOUS_URL_HASH b9e98a200d2455f06db9c661c5610496) -set(TA_TRACKED_MADNESS_TAG b378fd6f1fcadf1cd1ce4541ca4100c335b874ee) -set(TA_TRACKED_MADNESS_PREVIOUS_TAG dbda9f901134314eb73deb0ec5b499d178556642) +set(TA_TRACKED_MADNESS_TAG 7ce06234c23aa8e0ab3d9e9b87eff9cd85390d80) +set(TA_TRACKED_MADNESS_PREVIOUS_TAG b378fd6f1fcadf1cd1ce4541ca4100c335b874ee) set(TA_TRACKED_MADNESS_VERSION 0.10.1) set(TA_TRACKED_MADNESS_PREVIOUS_VERSION 0.10.1) diff --git a/src/TiledArray/distributed_storage.h b/src/TiledArray/distributed_storage.h index 030ed91205..a8ae5eb0d6 100644 --- a/src/TiledArray/distributed_storage.h +++ b/src/TiledArray/distributed_storage.h @@ -71,13 +71,15 @@ class DistributedStorage : public madness::WorldObject > { DistributedStorage(const DistributedStorage_&); DistributedStorage_& operator=(const DistributedStorage_&); - void set_handler(const size_type i, const value_type& value) { + template + std::enable_if_t,value_type>, void> + set_handler(const size_type i, Value&& value) { future& f = get_local(i); // Check that the future has not been set already. TA_ASSERT(!f.probe() && "Tile has already been assigned."); - f.set(value); + f.set(std::forward(value)); } void get_handler(const size_type i, @@ -87,8 +89,10 @@ class DistributedStorage : public madness::WorldObject > { remote_f.set(f); } - void set_remote(const size_type i, const value_type& value) { - WorldObject_::task(owner(i), &DistributedStorage_::set_handler, i, value, + template + std::enable_if_t,value_type> || std::is_same_v,future>, void> + set_remote(const size_type i, Value&& value) { + WorldObject_::task(owner(i), &DistributedStorage_::set_handler&>, i, std::forward(value), madness::TaskAttributes::hipri()); } @@ -249,7 +253,8 @@ class DistributedStorage : public madness::WorldObject > { /// \param i The element to be set /// \param value The value of element \c i /// \throw TiledArray::Exception If \c i is greater than or equal to \c - /// max_size() . \throw madness::MadnessException If \c i has already been + /// max_size() . + /// \throw madness::MadnessException If \c i has already been /// set. void set(size_type i, const value_type& value) { TA_ASSERT(i < max_size_); @@ -259,6 +264,22 @@ class DistributedStorage : public madness::WorldObject > { set_remote(i, value); } + /// Set element \c i with \c value + + /// \param i The element to be set + /// \param value The value of element \c i + /// \throw TiledArray::Exception If \c i is greater than or equal to \c + /// max_size() . + /// \throw madness::MadnessException If \c i has already been + /// set. + void set(size_type i, value_type&& value) { + TA_ASSERT(i < max_size_); + if (is_local(i)) + set_handler(i, std::move(value)); + else + set_remote(i, std::move(value)); + } + /// Set element \c i with a \c Future \c f /// The owner of \c i may be local or remote. If \c i is remote, a task