Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
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
46 changes: 6 additions & 40 deletions BuildMemo.md
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ If you prefer to install Anaconda, please make sure to download the correct vers

Download and install CMake https://cmake.org/download/

CMake version must > 3.16.0 to compile igraph.
CMake 3.18 or newer is required to compile the native extension.

Remember to add CMake to your path.

Expand Down Expand Up @@ -99,12 +99,11 @@ cppsrc/lib/
└── simulator-core.lib # simulator-core library for Windows
```

Then install or pack the package
Then install or build a wheel. These commands use the active Python interpreter and install the build-only dependencies declared in `pyproject.toml` in an isolated environment.

```
python setup.py install # install at local
python setup.py bdist_wheel # pack to a binary wheel, must first pip install wheel
python setup.py sdist # pack to a tar.gz of src
python -m pip install .
python -m pip wheel --no-deps .
```

### Issues
Expand All @@ -120,40 +119,7 @@ Call Stack (most recent call first):
/Users/spinq/Desktop/CMake.app/Contents/share/cmake-3.22/Modules/FindPackageHandleStandardArgs.cmake:594 (_FPHSA_FAILURE_MESSAGE)
```

To fix this, you need to add `PYTHON_INCLUDE_DIR` and `PYTHON_LIBRARY` at line 56 of `setup.py`

Windows Sample

```python
cmake_args = [
'-DPYTHON_INCLUDE_DIR=D:/tools/miniconda3/envs/python38/include',
'-DPYTHON_LIBRARY=D:/tools/miniconda3/envs/python38/libs/python38.lib',
'-DCMAKE_LIBRARY_OUTPUT_DIRECTORY=' + extdir,
'-DPYTHON_EXECUTABLE=' + sys.executable
]
```

Mac Sample

```python
cmake_args = [
'-DPYTHON_INCLUDE_DIR=/Library/Developer/CommandLineTools/Library/Frameworks/Python3.framework/Versions/3.8/include/python3.8',
'-DPYTHON_LIBRARY=/Library/Developer/CommandLineTools/Library/Frameworks/Python3.framework/Versions/3.8/lib/libpython3.8.dylib',
'-DCMAKE_LIBRARY_OUTPUT_DIRECTORY=' + extdir,
'-DPYTHON_EXECUTABLE=' + sys.executable
]
```

Linux Sample

```python
cmake_args = [
'-DPYTHON_INCLUDE_DIR=/home/hx/.conda/envs/python38/include/python3.8',
'-DPYTHON_LIBRARY=/home/hx/.conda/envs/python38/lib/libpython3.8.so',
'-DCMAKE_LIBRARY_OUTPUT_DIRECTORY=' + extdir,
'-DPYTHON_EXECUTABLE=' + sys.executable
]
```
Use `python -m pip install .` from the intended environment. The build passes that interpreter and the isolated `pybind11` CMake directory explicitly; manual edits to `setup.py` should not be necessary.

#### 2

Expand All @@ -180,4 +146,4 @@ ERROR: Could not install packages due to an OSError: [Errno 13] Permission denie
Consider using the `--user` option or check the permissions.
```

Check premission, use `sudo` or `--user` for installation
Check premission, use `sudo` or `--user` for installation
26 changes: 6 additions & 20 deletions CMakeLists.txt
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
cmake_minimum_required(VERSION 3.12)
cmake_minimum_required(VERSION 3.18)

set(CMAKE_C_STANDARD 99)
set(CMAKE_C_STANDARD_REQUIRED True)
Expand All @@ -11,29 +11,15 @@ endif ()

project(spinqit VERSION 0.0.1)

find_package(Python 3.8 COMPONENTS Interpreter Development.Module REQUIRED)
set(PYBIND11_FINDPYTHON ON)
find_package(pybind11 CONFIG REQUIRED)

add_subdirectory(cppsrc)

set(WRAPPER_DIR "spinqit/backend/wrapper")
set(SOURCES "${WRAPPER_DIR}/backend_binding.cpp")

find_package(PythonLibs 3 REQUIRED)
set(_find_pybind_cmake_command "
import sys
import pybind11
sys.stdout.write(pybind11.get_cmake_dir())
")

execute_process(COMMAND "${PYTHON_EXECUTABLE}" -c "${_find_pybind_cmake_command}"
OUTPUT_VARIABLE _pybind_cmake
RESULT_VARIABLE _pybind_cresult)

message(STATUS "PYBIND CMAKE: ${_pybind_cmake}")

set(pybind11_DIR "${_pybind_cmake}")

message(STATUS "PYBIND11 dir: ${pybind11_DIR}")
find_package(pybind11 REQUIRED)

pybind11_add_module(spinq_backends ${SOURCES})
target_include_directories(spinq_backends PRIVATE "${CMAKE_CURRENT_LIST_DIR}/cppsrc/include"
"${CMAKE_CURRENT_LIST_DIR}/cppsrc/basic_simulator/include"
Expand All @@ -45,4 +31,4 @@ set_target_properties(spinq_backends PROPERTIES
BUILD_RPATH "\$ORIGIN"
)

target_link_libraries(spinq_backends PRIVATE spinq-simulator)
target_link_libraries(spinq_backends PRIVATE spinq-simulator)
5 changes: 5 additions & 0 deletions MANIFEST.in
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
include CMakeLists.txt
graft cppsrc
graft spinqit/backend/wrapper
graft tests
global-exclude __pycache__ *.py[cod] .DS_Store
2 changes: 1 addition & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ SpinQit is the quantum software development kit from SpinQ Technology Co., Ltd.
## Installation and Documentation

- SpinQit is available on Windows, Linux and MacOS. Only the **Windows** version can use a local quantum computer as a backend. This package has been tested on Ubuntu 20.04 & 22.04 (x86_64), Windows 10 (x86_64), MacOS Ventura 13.0 (M1, M2) and MacOS Mojave 10.14.6 (x86_64).
- SpinQit requires Python 3.8+. This package has been tested with Python 3.8.13 and 3.9.12.
- SpinQit supports Python 3.8 through 3.12.
- We suggest you use Anaconda to set up your Python environment.

SpinQit can be installed using the following command:
Expand Down
29 changes: 3 additions & 26 deletions cppsrc/CMakeLists.txt
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
cmake_minimum_required(VERSION 3.12)
cmake_minimum_required(VERSION 3.18)

set(CMAKE_CXX_STANDARD 14)
set(CMAKE_CXX_STANDARD_REQUIRED ON)
Expand All @@ -9,28 +9,6 @@ endif ()

project(spinq-simulator VERSION 0.0.1)

find_package(PythonLibs REQUIRED)

message(STATUS "PYTHON include dirs: ${PYTHON_INCLUDE_DIRS}")

set(_find_pybind_includes_command "
import sys
import pybind11
sys.stdout.write(pybind11.get_include())
")

execute_process(COMMAND "${PYTHON_EXECUTABLE}" -c "${_find_pybind_includes_command}"
OUTPUT_VARIABLE _pybind_output
RESULT_VARIABLE _pybind_result)

if(_pybind_result EQUAL "0")
message(STATUS "PYCOMM RAW: ${_pybind_output}")
set(PYBIND_INCLUDE_DIRS "${_pybind_output}")
else()
message(WARNING "(NAIVE) CHECK COULD NOT FIND PYBIND!")
set(PYBIND_INCLUDE_DIRS ${PYTHON_INCLUDE_DIRS})
endif()

# Source files
file(GLOB_RECURSE SOURCE_FILES CONFIGURE_DEPENDS "*.cpp" "*.h")

Expand Down Expand Up @@ -79,8 +57,7 @@ add_library(spinq-simulator STATIC ${SOURCE_FILES})
target_include_directories(spinq-simulator PUBLIC ${CMAKE_CURRENT_LIST_DIR}/basic_simulator/include
${CMAKE_CURRENT_LIST_DIR}/nmr/include
${CMAKE_CURRENT_LIST_DIR}/include
${PYTHON_INCLUDE_DIRS}
${PYBIND_INCLUDE_DIRS})
${Python_INCLUDE_DIRS})

set_target_properties(spinq-simulator PROPERTIES
BUILD_WITH_INSTALL_RPATH TRUE
Expand All @@ -92,6 +69,6 @@ target_link_libraries(spinq-simulator PUBLIC
${CORE_LIB}
${IGRAPH_LIB}
${QUASAR_LIB}
pybind11::headers
Threads::Threads
)

12 changes: 5 additions & 7 deletions cppsrc/basic_simulator/include/basic_simulator.h
Original file line number Diff line number Diff line change
Expand Up @@ -42,24 +42,22 @@ namespace py = pybind11;

using namespace std;

extern "C" {
#include "util/graph_attributes.h"
#include "igraph/igraph.h"
}
#include "util/graph_data.h"

class BasicSimulator
{
public:
BasicSimulator();
~BasicSimulator();

Result execute(py::capsule graph, py::dict config)
Result execute(py::dict graph_data, py::dict config)
{
Result re;
vector<StateType> sv;
vector<double> ps;

igraph_t *gptr = (igraph_t *)graph.get_pointer();
NativeGraph graph(graph_data);
igraph_t *gptr = graph.get();
igraph_vector_t vs_res;
igraph_vector_init(&vs_res, 0);
igraph_topological_sorting(gptr, &vs_res, IGRAPH_OUT);
Expand Down Expand Up @@ -153,4 +151,4 @@ class BasicSimulator
};


#endif
#endif
8 changes: 4 additions & 4 deletions cppsrc/include/util/graph_attributes.h
Original file line number Diff line number Diff line change
Expand Up @@ -22,8 +22,8 @@
#include <igraph/igraph_error.h>

#define PyBaseString_Check(o) (PyUnicode_Check(o) || PyBytes_Check(o))
#define ATTR_STRUCT(graph) ((igraphmodule_i_attribute_struct*)((graph)->attr))
#define ATTR_STRUCT_DICT(graph) ((igraphmodule_i_attribute_struct*)((graph)->attr))->attrs
#define ATTR_STRUCT(graph) ((spinqit_attribute_struct*)((graph)->attr))
#define ATTR_STRUCT_DICT(graph) ((spinqit_attribute_struct*)((graph)->attr))->attrs

#define ATTRHASH_IDX_GRAPH 0
#define ATTRHASH_IDX_VERTEX 1
Expand All @@ -32,7 +32,7 @@
typedef struct {
PyObject* attrs[3];
PyObject* vertex_name_index;
} igraphmodule_i_attribute_struct;
} spinqit_attribute_struct;

/*
* Copy unicode bytes to a string
Expand Down Expand Up @@ -418,4 +418,4 @@ static int topological_sorting_from_vertex(const igraph_t *graph,

igraph_vector_destroy(&dfs_res);
return 0;
}
}
71 changes: 71 additions & 0 deletions cppsrc/include/util/graph_data.h
Original file line number Diff line number Diff line change
@@ -0,0 +1,71 @@
#pragma once

#include <stdexcept>

#include <pybind11/pybind11.h>

extern "C" {
#include "igraph/igraph.h"
#include "util/graph_attributes.h"
}

class NativeGraph
{
public:
explicit NativeGraph(pybind11::dict data) : data_(data)
{
pybind11::list edges = data_["edges"];
igraph_vector_t edge_vector;
if (igraph_vector_init(&edge_vector, edges.size() * 2) != IGRAPH_SUCCESS) {
throw std::runtime_error("Could not allocate the native graph edge vector.");
}

int status;
try {
for (pybind11::ssize_t i = 0; i < edges.size(); ++i) {
pybind11::sequence edge = edges[i];
VECTOR(edge_vector)[i * 2] = edge[0].cast<igraph_integer_t>();
VECTOR(edge_vector)[i * 2 + 1] = edge[1].cast<igraph_integer_t>();
}

status = igraph_create(
&graph_,
&edge_vector,
data_["vertex_count"].cast<igraph_integer_t>(),
data_["directed"].cast<bool>()
);
} catch (...) {
igraph_vector_destroy(&edge_vector);
throw;
}
igraph_vector_destroy(&edge_vector);
if (status != IGRAPH_SUCCESS) {
throw std::runtime_error("Could not create the native graph.");
}

attributes_.attrs[ATTRHASH_IDX_GRAPH] = data_["graph_attrs"].ptr();
attributes_.attrs[ATTRHASH_IDX_VERTEX] = data_["vertex_attrs"].ptr();
attributes_.attrs[ATTRHASH_IDX_EDGE] = data_["edge_attrs"].ptr();
attributes_.vertex_name_index = nullptr;
graph_.attr = &attributes_;
}

~NativeGraph()
{
graph_.attr = nullptr;
igraph_destroy(&graph_);
}

NativeGraph(const NativeGraph&) = delete;
NativeGraph& operator=(const NativeGraph&) = delete;

igraph_t* get()
{
return &graph_;
}

private:
pybind11::dict data_;
spinqit_attribute_struct attributes_;
igraph_t graph_;
};
12 changes: 5 additions & 7 deletions cppsrc/nmr/include/nmr.h
Original file line number Diff line number Diff line change
Expand Up @@ -44,10 +44,7 @@ using namespace std;

#include "SpinQuasar.h"

extern "C" {
#include "util/graph_attributes.h"
#include "igraph/igraph.h"
}
#include "util/graph_data.h"

inline string convert_to_binary(size_t i, size_t n)
{
Expand All @@ -62,7 +59,7 @@ class Nmr
{
public:
Nmr() {}
Result execute(py::capsule graph, py::dict config)
Result execute(py::dict graph_data, py::dict config)
{
Result re;
string ip = "127.0.0.1";
Expand Down Expand Up @@ -113,7 +110,8 @@ class Nmr
verbose = pcobj.cast<bool>();
}

igraph_t *gptr = (igraph_t *)graph.get_pointer();
NativeGraph graph(graph_data);
igraph_t *gptr = graph.get();
vector<Operation> gate_map;
int qnum = translate(gptr, gate_map);

Expand Down Expand Up @@ -167,4 +165,4 @@ class Nmr
int translate(const igraph_t *g, vector<Operation> & gate_map);
};

#endif
#endif
3 changes: 1 addition & 2 deletions doc/GettingStarted.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@
## Requirements

- SpinQit is available on Windows, Linux and MacOS. Only the **Windows** version can use a local quantum computer as a backend. This package has been tested on Ubuntu 20.04 & 22.04 (x86_64), Windows 10 (x86_64), MacOS Ventura 13.0 (M1, M2) and MacOS Mojave 10.14.6 (x86_64).
- SpinQit requires Python 3.8+. This package has been tested with Python 3.8.13 and 3.9.12.
- SpinQit supports Python 3.8 through 3.12.
- We suggest you use Anaconda to set up your Python environment. Please refer to [https://docs.anaconda.com/anaconda/](https://docs.anaconda.com/anaconda/) about how to install and use a conda environment. On Windows, we recommend adding Anaconda to your PATH environment viarable to avoid unnecessary troubles.
## Installation
SpinQit can be installed using the following command:
Expand Down Expand Up @@ -2136,4 +2136,3 @@ html.writer-html5 .rst-content table td:nth-child(2) p{
margin-bottom: 12px !important;
}
</style>

8 changes: 8 additions & 0 deletions pyproject.toml
Original file line number Diff line number Diff line change
@@ -0,0 +1,8 @@
[build-system]
requires = [
"setuptools>=61",
"wheel",
"cmake>=3.18",
"pybind11>=2.11,<4",
]
build-backend = "setuptools.build_meta"
Loading