Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[WIP] Operators and Integration with cudensitymat #2407

Draft
wants to merge 25 commits into
base: main
Choose a base branch
from
Draft
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
25 commits
Select commit Hold shift + click to select a range
3280517
Merge in dynamics work and squash commit history (#12)
anthony-santana Jan 9, 2025
ecbd5f7
Cleaning up docs preview for PR #12.
cuda-quantum-bot Jan 9, 2025
429dbf4
fixing spellings
sacpis Jan 9, 2025
7acf7cd
Adding base_integrator and base_time_stepper
sacpis Jan 9, 2025
f00ee1b
adding base_operators interface
sacpis Jan 13, 2025
064b279
keeping degrees to match the current implementation
sacpis Jan 13, 2025
8e1a89a
adding base integrator and time stepper
sacpis Jan 13, 2025
dd7e9cc
* Adding base test cases for Runge-Kutta stepper and integrator
sacpis Jan 14, 2025
5231a9c
* Adding helpers functionlity
sacpis Jan 14, 2025
d18f186
Formatting
sacpis Jan 14, 2025
c3e49a7
Adding evolution API header
sacpis Jan 15, 2025
49911d3
Formatting
sacpis Jan 15, 2025
3a2597f
Replacing Eigen::MatrixXcd with matrix_2
sacpis Jan 15, 2025
ccbe2c4
* Adding Rydberg hamiltonian operator
sacpis Jan 16, 2025
35a1040
Adding interface for cudm_helpers
sacpis Jan 16, 2025
3abcdca
Changing matrix to operator_sum
sacpis Jan 16, 2025
5a93c98
cudm_helpers implementation
sacpis Jan 21, 2025
985b6cf
Formatting
sacpis Jan 21, 2025
c9ec5ae
* Adding macro for handling error
sacpis Jan 21, 2025
1a4c5b6
Adding MACRO for error handling
sacpis Jan 22, 2025
7303ab2
Fixing convert_to_cudensitymat_operator as per the cudensitymat APIs
sacpis Jan 22, 2025
7d69ae7
Updating CMakeLists and unittests
sacpis Jan 22, 2025
06b720f
* Adding vector of cudensitymatElementaryOperator_t to store and destroy
sacpis Jan 23, 2025
b592f8a
Refactoring the code
sacpis Jan 23, 2025
b9c86ef
Fixing the matrix in the unittest and other code in compute_lindblad …
sacpis Jan 23, 2025
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
47 changes: 47 additions & 0 deletions docs/sphinx/api/languages/cpp_api.rst
Original file line number Diff line number Diff line change
Expand Up @@ -223,6 +223,53 @@ Utilities
.. doxygentypedef:: cudaq::real

.. doxygenfunction:: cudaq::range(std::size_t)

Dynamics
=========

.. .. doxygenclass:: cudaq::EvolveResult
:members:

.. .. doxygenclass:: cudaq::AsyncEvolveResult
:members:

.. doxygenclass:: cudaq::operator_sum
:members:

.. doxygenclass:: cudaq::product_operator
:members:

.. doxygenclass:: cudaq::scalar_operator
:members:

.. doxygenclass:: cudaq::elementary_operator
:members:

.. doxygenclass:: cudaq::OperatorArithmetics
:members:

.. doxygenclass:: cudaq::MatrixArithmetics
:members:

.. doxygenclass:: cudaq::Schedule
:members:

.. doxygenclass:: cudaq::operators
:members:

.. doxygenclass:: cudaq::pauli
:members:

.. .. doxygenfunction:: cudaq::evolve(Operator hamiltonian, std::map<int,int> dimensions, Schedule schedule, bool store_intermediate_states)

.. .. doxygenfunction:: cudaq::evolve(Operator hamiltonian, std::map<int,int> dimensions, Schedule schedule, std::vector<Operator> collapse_operators, std::vector<Operator> observables, bool store_intermediate_states)

.. .. doxygenfunction:: cudaq::evolve(Operator hamiltonian, std::map<int,int> dimensions, Schedule schedule, state initial_state, std::vector<Operator> collapse_operators, std::vector<Operator> observables, bool store_intermediate_states)

.. .. doxygenfunction:: cudaq::evolve(Operator hamiltonian, std::map<int,int> dimensions, Schedule schedule, std::vector<state> initial_states, std::vector<Operator> collapse_operators, std::vector<Operator> observables, bool store_intermediate_states)

.. .. doxygenfunction:: cudaq::evolve_async


Namespaces
===========
Expand Down
5 changes: 3 additions & 2 deletions runtime/cudaq/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -40,7 +40,7 @@ if (CUDA_FOUND)
PRIVATE .)

target_link_libraries(${LIBRARY_NAME}
PUBLIC dl cudaq-spin cudaq-common cudaq-nlopt cudaq-ensmallen
PUBLIC dl cudaq-spin cudaq-operators cudaq-common cudaq-nlopt cudaq-ensmallen
PRIVATE nvqir fmt::fmt-header-only CUDA::cudart_static)

target_compile_definitions(${LIBRARY_NAME} PRIVATE CUDAQ_HAS_CUDA)
Expand All @@ -52,7 +52,7 @@ else()
PRIVATE .)

target_link_libraries(${LIBRARY_NAME}
PUBLIC dl cudaq-spin cudaq-common cudaq-nlopt cudaq-ensmallen
PUBLIC dl cudaq-spin cudaq-operators cudaq-common cudaq-nlopt cudaq-ensmallen
PRIVATE nvqir fmt::fmt-header-only)
endif()

Expand All @@ -61,6 +61,7 @@ add_subdirectory(algorithms)
add_subdirectory(platform)
add_subdirectory(builder)
add_subdirectory(domains)
add_subdirectory(dynamics)

install(TARGETS ${LIBRARY_NAME} EXPORT cudaq-targets DESTINATION lib)

Expand Down
55 changes: 55 additions & 0 deletions runtime/cudaq/base_integrator.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,55 @@
/****************************************************************-*- C++ -*-****
* Copyright (c) 2022 - 2025 NVIDIA Corporation & Affiliates. *
* All rights reserved. *
* *
* This source code and the accompanying materials are made available under *
* the terms of the Apache License 2.0 which accompanies this distribution. *
******************************************************************************/

#pragma once

#include "base_time_stepper.h"
#include "operators.h"
#include "schedule.h"
#include <map>
#include <memory>
#include <vector>

namespace cudaq {
template <typename TState>
class BaseIntegrator {
protected:
std::map<std::string, double> integrator_options;
TState state;
double t;
std::map<int, int> dimensions;
std::shared_ptr<Schedule> schedule;
std::shared_ptr<operator_sum> hamiltonian;
std::shared_ptr<BaseTimeStepper<TState>> stepper;
std::vector<std::shared_ptr<operator_sum>> collapse_operators;

virtual void post_init() = 0;

public:
virtual ~BaseIntegrator() = default;

void set_state(const TState &initial_state, double t0 = 0.0) {
state = initial_state;
t = t0;
}

void set_system(
const std::map<int, int> &dimensions, std::shared_ptr<Schedule> schedule,
std::shared_ptr<operator_sum> hamiltonian,
std::vector<std::shared_ptr<operator_sum>> collapse_operators = {}) {
this->dimensions = dimensions;
this->schedule = schedule;
this->hamiltonian = hamiltonian;
this->collapse_operators = collapse_operators;
}

virtual void integrate(double t) = 0;

std::pair<double, TState> get_state() const { return {t, state}; }
};
} // namespace cudaq
19 changes: 19 additions & 0 deletions runtime/cudaq/base_time_stepper.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
/****************************************************************-*- C++ -*-****
* Copyright (c) 2022 - 2025 NVIDIA Corporation & Affiliates. *
* All rights reserved. *
* *
* This source code and the accompanying materials are made available under *
* the terms of the Apache License 2.0 which accompanies this distribution. *
******************************************************************************/

#pragma once

namespace cudaq {
template <typename TState>
class BaseTimeStepper {
public:
virtual ~BaseTimeStepper() = default;

virtual void compute(TState &state, double t, double step_size) = 0;
};
} // namespace cudaq
30 changes: 30 additions & 0 deletions runtime/cudaq/cudm_error_handling.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
/****************************************************************-*- C++ -*-****
* Copyright (c) 2022 - 2025 NVIDIA Corporation & Affiliates. *
* All rights reserved. *
* *
* This source code and the accompanying materials are made available under *
* the terms of the Apache License 2.0 which accompanies this distribution. *
******************************************************************************/

#pragma once
#include <cudensitymat.h>
#include <fmt/core.h>
#include <stdexcept>

#define HANDLE_CUDM_ERROR(x) \
{ \
const auto err = x; \
if (err != CUDENSITYMAT_STATUS_SUCCESS) { \
throw std::runtime_error(fmt::format("[cudaq] %{} in {} (line {})", err, \
__FUNCTION__, __LINE__)); \
} \
}

#define HANDLE_CUDA_ERROR(x) \
{ \
const auto err = x; \
if (err != cudaSuccess) { \
throw std::runtime_error(fmt::format("[cuda] %{} in {} (line {})", err, \
__FUNCTION__, __LINE__)); \
} \
}
43 changes: 43 additions & 0 deletions runtime/cudaq/cudm_helpers.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,43 @@
/****************************************************************-*- C++ -*-****
* Copyright (c) 2022 - 2025 NVIDIA Corporation & Affiliates. *
* All rights reserved. *
* *
* This source code and the accompanying materials are made available under *
* the terms of the Apache License 2.0 which accompanies this distribution. *
******************************************************************************/

#pragma once

#include "cudaq/operators.h"
#include "cudaq/utils/tensor.h"
#include <cudensitymat.h>
#include <iostream>
#include <map>
#include <stdexcept>
#include <vector>

namespace cudaq {
cudensitymatState_t initialize_state(cudensitymatHandle_t handle,
cudensitymatStatePurity_t purity,
const std::vector<int64_t> &mode_extents);

void scale_state(cudensitymatHandle_t handle, cudensitymatState_t state,
double scale_factor, cudaStream_t stream);

void destroy_state(cudensitymatState_t state);

cudensitymatOperator_t
compute_lindblad_operator(cudensitymatHandle_t handle,
const std::vector<matrix_2> &c_ops,
const std::vector<int64_t> &mode_extents);

cudensitymatOperator_t convert_to_cudensitymat_operator(
cudensitymatHandle_t handle,
const std::map<std::string, std::complex<double>> &parameters,
const operator_sum &op, const std::vector<int64_t> &mode_extents);

cudensitymatOperator_t construct_liovillian(
cudensitymatHandle_t handle, const cudensitymatOperator_t &hamiltonian,
const std::vector<cudensitymatOperator_t> &collapse_operators,
double gamma);
} // namespace cudaq
136 changes: 136 additions & 0 deletions runtime/cudaq/definition.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,136 @@
/****************************************************************-*- C++ -*-****
* Copyright (c) 2022 - 2024 NVIDIA Corporation & Affiliates. *
* All rights reserved. *
* *
* This source code and the accompanying materials are made available under *
* the terms of the Apache License 2.0 which accompanies this distribution. *
******************************************************************************/

#include "cudaq/qis/state.h"
#include "cudaq/utils/tensor.h"

#include <complex>
#include <functional>
#include <iostream>
#include <map>
#include <string>
#include <vector>

namespace cudaq {

// Limit the signature of the users callback function to accept a vector of ints
// for the degree of freedom dimensions, and a vector of complex doubles for the
// concrete parameter values.
using Func = std::function<matrix_2(
std::map<int, int>, std::map<std::string, std::complex<double>>)>;

class CallbackFunction {
private:
// The user provided callback function that takes the degrees of
// freedom and a vector of complex parameters.
Func _callback_func;

public:
CallbackFunction() = default;

template <typename Callable>
CallbackFunction(Callable &&callable) {
static_assert(
std::is_invocable_r_v<matrix_2, Callable, std::map<int, int>,
std::map<std::string, std::complex<double>>>,
"Invalid callback function. Must have signature "
"matrix_2("
"std::map<int,int>, "
"std::map<std::string, std::complex<double>>)");
_callback_func = std::forward<Callable>(callable);
}

// Copy constructor.
CallbackFunction(CallbackFunction &other) {
_callback_func = other._callback_func;
}

CallbackFunction(const CallbackFunction &other) {
_callback_func = other._callback_func;
}

matrix_2
operator()(std::map<int, int> degrees,
std::map<std::string, std::complex<double>> parameters) const {
return _callback_func(std::move(degrees), std::move(parameters));
}
};

using ScalarFunc = std::function<std::complex<double>(
std::map<std::string, std::complex<double>>)>;

// A scalar callback function does not need to accept the dimensions,
// therefore we will use a different function type for this specific class.
class ScalarCallbackFunction : CallbackFunction {
private:
// The user provided callback function that takes a vector of parameters.
ScalarFunc _callback_func;

public:
ScalarCallbackFunction() = default;

template <typename Callable>
ScalarCallbackFunction(Callable &&callable) {
static_assert(
std::is_invocable_r_v<std::complex<double>, Callable,
std::map<std::string, std::complex<double>>>,
"Invalid callback function. Must have signature std::complex<double>("
"std::map<std::string, std::complex<double>>)");
_callback_func = std::forward<Callable>(callable);
}

// Copy constructor.
ScalarCallbackFunction(ScalarCallbackFunction &other) {
_callback_func = other._callback_func;
}

ScalarCallbackFunction(const ScalarCallbackFunction &other) {
_callback_func = other._callback_func;
}

bool operator!() { return (!_callback_func); }

std::complex<double>
operator()(std::map<std::string, std::complex<double>> parameters) const {
return _callback_func(std::move(parameters));
}
};

/// @brief Object used to give an error if a Definition of an elementary
/// or scalar operator is instantiated by other means than the `define`
/// class method.
class Definition {
public:
std::string id;

// The user-provided generator function should take a variable number of
// complex doubles for the parameters. It should return a
// `cudaq::tensor` type representing the operator
// matrix.
CallbackFunction generator;

// Constructor.
Definition();

// Destructor.
~Definition();

void create_definition(const std::string &operator_id,
std::map<int, int> expected_dimensions,
CallbackFunction &&create);

// To call the generator function
matrix_2 generate_matrix(
const std::map<int, int> &degrees,
const std::map<std::string, std::complex<double>> &parameters) const;

private:
// Member variables
std::map<int, int> m_expected_dimensions;
};
} // namespace cudaq
Loading
Loading