...
 
Commits (5)
......@@ -57,7 +57,7 @@ int main(int argc, char **argv) {
// Get reference to the Accelerator
auto accelerator =
xacc::getAccelerator("tnqvm", {{"tnqvm-visitor", "exatn-mps"}});
xacc::getAccelerator("tnqvm", {{"tnqvm-visitor", "exatn"}});
// Decorate the accelerator with HPC Virtualization.
// This decorator assumes the provided number of input QPUs
......
......@@ -22,7 +22,7 @@ int main(int argc, char **argv) {
// Get reference to the Accelerator
auto accelerator =
xacc::getAccelerator("tnqvm", {{"tnqvm-visitor", "exatn-mps"}});
xacc::getAccelerator("tnqvm", {{"tnqvm-visitor", "exatn"}});
// Decorate the accelerator with HPC Virtualization.
// This decorator assumes the provided number of input QPUs
......
......@@ -166,7 +166,9 @@ ObservedAnsatz ObservedAnsatz::fromObservedComposites(
auto comp = in_composites[i];
auto iter = matchedIters[i];
auto newComp =
gateRegistry->createComposite("__OBSERVED__" + comp->name());
// IMPORTANT: the sub-circuit must keep the same name as the
// composite since downstream mapping depends on this.
gateRegistry->createComposite(comp->name());
// Add the remaining instructions
while (iter.hasNext()) {
......
......@@ -29,6 +29,14 @@ void HPCVirtDecorator::initialize(const HeterogeneousMap &params) {
decoratedAccelerator->initialize(params);
if (params.keyExists<int>("n-virtual-qpus")) {
if (qpuComm && n_virtual_qpus != params.get<int>("n-virtual-qpus")) {
// We don't support changing the number of virtual QPU's
// i.e. between xacc::Initialize and xacc::Finalize,
// we must use an HPCVirtDecorator with a consistent number of virtual
// QPU's.
xacc::error(
"Dynamically changing the number of virtual QPU's is not supported.");
}
n_virtual_qpus = params.get<int>("n-virtual-qpus");
}
......@@ -75,7 +83,16 @@ void HPCVirtDecorator::execute(
// Get the rank and size in the original communicator
int world_rank = world.rank(), world_size = world.size();
if (world_size <= n_virtual_qpus) {
if (world_size < n_virtual_qpus) {
// The number of MPI processes is less than the number of requested virtual
// QPUs, just execute as if there is only one virtual QPU and give the QPU
// the whole MPI_COMM_WORLD.
void *qpu_comm_ptr = reinterpret_cast<void *>((MPI_Comm)world);
if (!qpuComm) {
qpuComm = std::make_shared<boost::mpi::communicator>(world);
}
decoratedAccelerator->updateConfiguration(
{{"mpi-communicator", qpu_comm_ptr}});
// just execute
decoratedAccelerator->execute(buffer, functions);
return;
......@@ -86,8 +103,12 @@ void HPCVirtDecorator::execute(
// Split the communicator based on the color and use the
// original rank for ordering
auto qpu_comm = world.split(color, world_rank);
if (!qpuComm) {
// Splits MPI_COMM_WORLD into sub-communicators if not already.
qpuComm = std::make_shared<boost::mpi::communicator>(world.split(color, world_rank));
}
auto qpu_comm = *qpuComm;
// current rank now has a color to indicate which sub-comm it belongs to
// Give that sub communicator to the accelerator
void *qpu_comm_ptr = reinterpret_cast<void *>((MPI_Comm)qpu_comm);
......
......@@ -15,7 +15,12 @@
#include "AcceleratorDecorator.hpp"
#include "TearDown.hpp"
namespace boost {
namespace mpi {
// Forward declaration
class communicator;
} // namespace mpi
} // namespace boost
namespace xacc {
namespace quantum {
......@@ -25,7 +30,8 @@ protected:
std::string roErrorFile = "";
int n_virtual_qpus = 1;
// The MPI communitor for each QPU.
std::shared_ptr<boost::mpi::communicator> qpuComm;
public:
void initialize(const HeterogeneousMap &params = {}) override;
......