Commit f65e2e08 authored by Mccaskey, Alex's avatar Mccaskey, Alex
Browse files

updating docs with a few rigetti tutorials

parent 0c2b8e1b
XACC Tutorials
================
First off, make sure you have successfully built XACC (see `XACC Install <install.html>`_).
Rigetti Integration
====================
Installation
-------------
.. note::
If you want support for the Rigetti Accelerator, you must install
`CppRestSDK <https://github.com/microsoft/cpprestsdk>`_ and OpenSSL. This
is required for these Accelerators to make remote HTTP Rest calls to their
respective server APIs. Here's how to install these as binaries on various popular platforms:
.. code::
$ (macosx) brew install cpprestsdk
$ (fedora) dnf install cpprest-devel openssl-devel
$ (ubuntu) apt-get install libcpprest-dev libssl-dev
The `Rigetti Plugin <https://github.com/ornl-qci/xacc-rigetti>`_ provides
support to XACC for compiling kernels writting in Quil, and executing programs
on the Rigetti QVM via a Rigetti Accelerator.
To install this plugin, run the following
.. code::
$ xacc-install-plugins.py -p xacc-rigetti
You have now installed the Rigetti plugin. It is located in ``$XACC_ROOT/lib/plugins/accelerator``
and ``$XACC_ROOT/lib/plugins/compilers``, where ``XACC_ROOT`` is your XACC install prefix.
Rigetti Accelerator
--------------------
Rigetti Computing, Inc (`rigetti.com <rigetti.com>`_) is a recently founded startup that is focused on
developing quantum computing hardware and software and bring it to market.
They are working to build a cloud quantum computing platform for AI and
computational chemistry. They currently have a QVM simulation server
that can be accessed via a REST API with a private API key. Rigetti has
also done great work as of late in providing open source programming tools for
interfacing with their QVM - specifically, the PyQuil python framework
`PyQuil <https://github.com/rigetticomputing/pyquil>`_.
Recently, the ORNL QCI `(quantum.ornl.gov) <http://quantum.ornl.gov>`_, the XACC project,
and the Software and Applications Team from Rigetti have begun collaborating in
an effort to expose the Rigetti QVM server and programming tools to XACC and its user
community. This article describes the results of that work - specifically, a
new XACC Accelerator implementation that executes quantum kernels on the
Rigetti QVM server.
The ``RigettiAccelerator`` is an implementation or realization of the pluggable
XACC Accelerator interface. The RigettAccelerator class architecture diagram is
shown in Figure 1. The RigettiAccelerator's implementation of the Accelerator::execute() method
is charged with two primary tasks: (1) the translation of the XACC IR to an equivalent
Quil string, and (2) constructing and executing an
appropriate HTTPS Post on the Rigetti QVM server. The only remaining
thing to do once those two tasks are complete is to processes the resultant response from the server.
.. image:: ../assets/rigetti-acc-arch.png
Mapping XACC IR to Quil
^^^^^^^^^^^^^^^^^^^^^^^^
At its core, the XACC IR provides a tree-like, in-memory representation and API for a
compiled quantum kernel. The leaves of this tree are XACC Instructions and the nodes
of the tree are XACC Functions, which are composed of further child Instructions. The
XACC Quantum IR implementation provides a number of standard gate Instruction implementations
(Hadamard, CNOT, rotations, etc...) These serve as the leaves of the IR tree. These
instruction implementations know nothing of the Quil intermediate language and it would be tedious
and a poor design decision to to update the entire XACC Quantum IR package (we would have to do the
same for any and all current and future low-level languages). So XACC employs a common
software engineering design pattern to enable this XACC IR to Quil mapping: the
visitor pattern, which provides a mechansim for adding new operations to an
existing object without modifying the design of that object (`Visitor Pattern <https://en.wikipedia.org/wiki/Visitor_pattern>`_). For each derived gate Instruction, a Visitor class implements a
corresponding ``visit`` method (``visit(Hadamard& h)``, etc...). All gate instructions have the
ability to accept an incoming Visitor, and upon doing so, invoke the ``visit`` method that
corresponds to their type, thus giving the Visitor type information for the Gate Instruction.
Therefore, mapping to Quil simply involves walking the IR tree, and telling each Instruction to
accept the visitor:
.. code::
auto visitor = std::make_shared<QuilVisitor>();
InstructionIterator it(kernel);
while (it.hasNext()) {
// Get the next node in the tree
auto nextInst = it.next();
if (nextInst->isEnabled()) nextInst->accept(visitor);
}
auto quilStr = visitor->getQuilString();
The visitor implementation is known as the QuilVisitor, and its visit methods look like this (Hadamard for example):
.. code::
void visit(Hadamard& h) {
quilStr += "H " + std::to_string(h.bits()[0]) + "\n";
}
or for a more complicated gate Instruction:
.. code::
void visit(ConditionalFunction& c) {
auto visitor = std::make_shared<QuilVisitor>();
auto classicalBitIdx = qubitToClassicalBitIndex[c.getConditionalQubit()]; // populated in visit(Measure)
quilStr += "JUMP-UNLESS @" + c.getName() + " [" + std::to_string(classicalBitIdx) + "]\n";
for (auto inst : c.getInstructions()) {
inst->accept(visitor);
}
quilStr += visitor->getQuilString();
quilStr += "LABEL @" + c.getName() + "\n";
}
After walking the IR tree, the Quil representation is produced with a call to getQuilString().
Executing Quil code on Rigetti QVM
^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^
With the XACC IR mapped to Quil, the RigettiAccelerator is ready to execute
on the Rigetti QVM. The main task here is to construct the proper JSON payload string
that contains information about the type of the execution, the classical memory address
indices, and the Quil instructions string. The types of execution that the QVM allows are
multishot, multishot-measure, wavefunction, and expectation. In this work, we have primarily focused
on the multishot method. If the execution type is
multishot, then we can provide a further JSON key that is an integer that gives the
number of executions of the Quil code to run.
Rigetti QVM Tutorial
---------------------
Create a new directory called test-xacc-rigetti and cd into it. Let's now create a
test-xacc-rigetti.cpp file and get it started with the following boilerplate code:
.. code::
.. code-block:: cpp
#include "XACC.hpp"
......@@ -26,7 +149,7 @@ test-xacc-rigetti.cpp file and get it started with the following boilerplate cod
Building this code is straightforward with CMake. Create a CMakeLists.txt file in the same
directory as the test-xacc-rigetti.cpp file, and add the following to it:
.. code::
.. code-block:: cmake
# Start a CMake project
project(test-xacc-rigetti CXX)
......@@ -54,7 +177,7 @@ directory as the test-xacc-rigetti.cpp file, and add the following to it:
Now from within the test-xacc-rigetti directory, run the following:
.. code::
.. code-block:: bash
$ mkdir build
$ cd build
......@@ -63,7 +186,8 @@ Now from within the test-xacc-rigetti directory, run the following:
This will build test-xacc-rigetti.cpp and provide you with a test-xacc-rigetti executable. Run that
executable to ensure that your build worked (you should see the following output):
.. code::
.. code-block:: bash
$ make
$ ./test-xacc-rigetti
......@@ -79,7 +203,7 @@ Now that we have our build and initial boilerplate code setup, let's actually wr
teleporting the state of one qubit to another. Following the XACC.hpp include statement at the top of the file,
add the following quantum kernel declaration:
.. code::
.. code-block:: cpp
const std::string src("__qpu__ teleport (qbit qreg) {\n"
" cbit creg[3];\n"
......@@ -101,7 +225,7 @@ add the following quantum kernel declaration:
Now we are ready to build and execute this kernel using the XACC Runtime API. After the call
to xacc::Initialize, add the following:
.. code::
.. code-block:: cpp
// Create a reference to the Rigetti
// QPU at api.rigetti.com/qvm
......@@ -130,7 +254,8 @@ Finally, the user requests a reference to the executable kernel functor, and exe
provided register of qubits.
The total test-xacc-rigetti.cpp file should look like this:
.. code::
.. code-block:: cpp
#include "XACC.hpp"
......@@ -182,7 +307,8 @@ The total test-xacc-rigetti.cpp file should look like this:
}
Now, to build simple run:
.. code::
.. code-block:: bash
$ cd test-xacc-rigetti/build
$ make
......@@ -193,7 +319,7 @@ the same way you do with PyQuil (in your $HOME/.pyquil_config file, or in the $P
environment variable). You can also pass your API key to the XACC executable through the
--rigetti-api-key command line argument:
.. code::
.. code-block:: bash
$ ./test-xacc-rigetti --rigetti-api-key KEY
[2017-06-20 17:43:38.744] [xacc-console] [info] [xacc] Initializing XACC Framework
......@@ -214,7 +340,7 @@ You should see the console text printed above.
You can also tailor the number of executions that occur for the multishot execution type:
.. code::
.. code-block:: bash
$ ./test-xacc-rigetti --rigetti-trials 1000
[2017-06-20 17:50:57.285] [xacc-console] [info] [xacc] Initializing XACC Framework
......@@ -232,11 +358,128 @@ You can also tailor the number of executions that occur for the multishot execut
Note above we let XACC find the API Key in the standard .pyquil_config file.
XACC Python Bindings Tutorial
------------------------------
Executing PyQuil Code on any XACC Accelerator
----------------------------------------------
If you've installed the XACC Python Bindings (see here `<python.html#Installation>`_), then you can
actually take existing PyQuil code and execute it on any of the XACC Accelerators (Rigetti, IBM, TNQVM, any future ones coming online). You probably don't need to execute on the Rigetti Accelerator, since the Forest Python API
already provides that support. But this is a great way to run comparisons on our tensor network simulator or the
5 or 16 qubit IBM QPUs.
Check out the following example that uses PyQuil to program the VQE problem for
the Hydrogen molecule (code taken from `Scalable Quantum Simulation of Molecular Energies <https://arxiv.org/abs/1512.06860>`_ ).
.. note::
To run this, you must install pyQuil:
.. code::
$ pip install pyquil
.. code-block:: python
from pyquil.quil import Program
import pyquil.api as forest
from pyquil.gates import X, Z, H, CNOT, RX, RY, RZ
import numpy as np
import pyxacc as xacc
# Pyquil State Preparation circuit gen
def statePrep(qs, angle):
return Program(RX(np.pi, qs[0]),
RY(np.pi / 2, qs[1]),
RX(2.5*np.pi, qs[0]),
CNOT(qs[1],qs[0]),
RZ(angle, qs[0]),
CNOT(qs[1],qs[0]),
RY(2.5*np.pi, qs[1]),
RX(np.pi / 2, qs[0]))
# Z0 term of Hamiltonian
def Z0Term(qs, angle):
p = statePrep(qs,angle)
p.measure(qs[0],0)
return p
# Z1 term of Hamiltonian
def Z1Term(qs, angle):
p = statePrep(qs, angle)
p.measure(qs[1],0)
return p
# Z0Z1 term of Hamiltonian
def Z0Z1Term(qs, angle):
p = statePrep(qs, angle)
p.measure(qs[1],1)
p.measure(qs[0],0)
return p
# collect all generators in a list
terms = [Z0Term, Z1Term, Z0Z1Term]
# Initialize XACC
xacc.Initialize()
# turn on the QuilCompiler
xacc.setOption('compiler','quil')
# Get reference to our tensor network simulator
qpu = xacc.getAccelerator('tnqvm')
# create some qubits - an AcceleratorBuffer
qs = qpu.createBuffer('qs',2)
# Store results to this CSV file
file = open('pyquil_out.csv', 'w')
file.write('theta, Z0, Z1, Z0Z1\n')
# Pyquil uses int indices for qubits
pyquilQubits = [0,1]
# Loop -pi to pi
for theta in np.linspace(-np.pi,np.pi,100):
file.write(str(theta))
# Loop over our above generators
for t in terms:
file.write(', ')
# Kernel-ize the pyquil program
src = '__qpu__ kernel(AcceleratorBuffer qs, double theta) {\n'
src += t([0,1], theta).out()
src += '}'
# Create an XACC Program and compile
xaccProgram = xacc.Program(qpu, src)
xaccProgram.build()
# Get reference to the executable kernel
k = xaccProgram.getKernel('kernel')
# Execute, no params since theta has
# already been input to the term generator
k.execute(qs, [])
# Get the expectation value
e = qs.getExpectationValueZ()
# Reset the qubits for the next iteration
qs.resetBuffer()
file.write(str(e))
file.write('\n')
file.close()
# Finalize the framework.
xacc.Finalize()
This will produce a file called ``pyquil_out.csv``. Plotting this shows the
correct expectation values from the simulation.
.. image:: ../assets/pyquil_out.png
PyQuil-XACC Integration
------------------------
XACC D-Wave Markowitz Financial Modeling
-----------------------------------------
Scaffold
=========
Installation
-------------
.. note::
Due to issues getting `ScaffCC <https://github.com/ornl-qci/ScaffCC>`_ to link correctly with RTTI on Mac OS X, we do not have a binary package installer for Mac OS X. We are open to PRs on this if you can help.
To use the `Scaffold Plugin <https://github.com/ornl-qci/tnqvm>`_ you must have our fork of
Scaffold installed as a binary package. We have builds for Fedora 25/26 and Ubuntu 16.04/17.04. To install
.. code::
$ (fedora) dnf install https://github.com/ORNL-QCI/ScaffCC/releases/download/v2.0/scaffold-2.0-1.fc25.x86_64.rpm (REPLACE 25 with 26 if on FC26)
$ (ubuntu) wget https://github.com/ORNL-QCI/ScaffCC/releases/download/v2.0/scaffold_2.0_amd64.deb
$ (ubuntu) apt-get install -y $(dpkg --info scaffold_2.0_amd64.deb | grep Depends | sed "s/.*ends:\ //" | sed 's/,//g')
$ (ubuntu) dpkg -i scaffold_2.0_amd64.deb
To install this plugin, run the following
.. code::
$ xacc-install-plugins.py -p xacc-scaffold
You have now installed the Scaffold plugin. It is located in ``$XACC_ROOT/lib/plugins/compilers``, where ``XACC_ROOT`` is your XACC install prefix.
TNQVM
======
Installation
--------------
The `TNQVM Plugin <https://github.com/ornl-qci/tnqvm>`_ provides
support to XACC for executing programs
on the ORNL tensor network quantum virtual machine.
.. note::
This Accelerator requires BLAS/LAPACK libraries to be installed.
Here's how to install these as binaries on various popular platforms:
.. code::
$ (macosx) should already be there in Accelerate Framework, if not
$ (macosx) brew install openblas lapack
$ (fedora) dnf install blas-devel lapack-devel
$ (ubuntu) apt-get install libblas-dev liblapack-dev
To install this plugin, run the following
.. code::
$ xacc-install-plugins.py -p tnqvm
You have now installed the TNQVM plugin. It is located in ``$XACC_ROOT/lib/plugins/accelerator``, where ``XACC_ROOT`` is your XACC install prefix.
......@@ -101,7 +101,7 @@ add the following quantum kernel declaration:
Now we are ready to build and execute this kernel using the XACC Runtime API. After the call
to xacc::Initialize, add the following:
.. code::
.. code:: cpp
// Create a reference to the Rigetti
// QPU at api.rigetti.com/qvm
......@@ -238,3 +238,5 @@ XACC Python Bindings Tutorial
PyQuil-XACC Integration
------------------------
XACC D-Wave Markowitz Financial Modeling
-----------------------------------------
<!DOCTYPE html>
<!--[if IE 8]><html class="no-js lt-ie9" lang="en" > <![endif]-->
<!--[if gt IE 8]><!--> <html class="no-js" lang="en" > <!--<![endif]-->
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>D-Wave Integration &mdash; XACC 0.0.1 documentation</title>
<link rel="stylesheet" href="_static/css/theme.css" type="text/css" />
<link rel="index" title="Index"
href="genindex.html"/>
<link rel="search" title="Search" href="search.html"/>
<link rel="top" title="XACC 0.0.1 documentation" href="index.html"/>
<link rel="prev" title="IBM Integration" href="ibm.html"/>
<script src="_static/js/modernizr.min.js"></script>
</head>
<body class="wy-body-for-nav" role="document">
<div class="wy-grid-for-nav">
<nav data-toggle="wy-nav-shift" class="wy-nav-side">
<div class="wy-side-scroll">
<div class="wy-side-nav-search">
<a href="index.html" class="icon icon-home"> XACC
</a>
<div class="version">
0.0.1
</div>
<div role="search">
<form id="rtd-search-form" class="wy-form" action="search.html" method="get">
<input type="text" name="q" placeholder="Search docs" />
<input type="hidden" name="check_keywords" value="yes" />
<input type="hidden" name="area" value="default" />
</form>
</div>
</div>
<div class="wy-menu wy-menu-vertical" data-spy="affix" role="navigation" aria-label="main navigation">
<p class="caption"><span class="caption-text">Contents:</span></p>
<ul class="current">
<li class="toctree-l1"><a class="reference internal" href="overview.html">Getting started with XACC</a></li>
<li class="toctree-l1"><a class="reference internal" href="install.html">Installation</a></li>
<li class="toctree-l1"><a class="reference internal" href="api.html">XACC API</a></li>
<li class="toctree-l1"><a class="reference internal" href="python.html">XACC Python Bindings</a></li>
<li class="toctree-l1"><a class="reference internal" href="scaffold.html">Scaffold</a></li>
<li class="toctree-l1"><a class="reference internal" href="tnqvm.html">TNQVM</a></li>
<li class="toctree-l1"><a class="reference internal" href="rigetti.html">Rigetti Integration</a></li>
<li class="toctree-l1"><a class="reference internal" href="ibm.html">IBM Integration</a></li>
<li class="toctree-l1 current"><a class="current reference internal" href="#">D-Wave Integration</a><ul>
<li class="toctree-l2"><a class="reference internal" href="#installation">Installation</a><ul>
<li class="toctree-l3"><a class="reference internal" href="#extensibility-for-minor-graph-embedding-algorithms">Extensibility for Minor Graph Embedding Algorithms</a></li>
</ul>
</li>
</ul>
</li>
</ul>
</div>
</div>
</nav>
<section data-toggle="wy-nav-shift" class="wy-nav-content-wrap">
<nav class="wy-nav-top" role="navigation" aria-label="top navigation">
<i data-toggle="wy-nav-top" class="fa fa-bars"></i>
<a href="index.html">XACC</a>
</nav>
<div class="wy-nav-content">
<div class="rst-content">
<div role="navigation" aria-label="breadcrumbs navigation">
<ul class="wy-breadcrumbs">
<li><a href="index.html">Docs</a> &raquo;</li>
<li>D-Wave Integration</li>
<li class="wy-breadcrumbs-aside">
<a href="_sources/dwave.rst.txt" rel="nofollow"> View page source</a>
</li>
</ul>
<hr/>
</div>
<div role="main" class="document" itemscope="itemscope" itemtype="http://schema.org/Article">
<div itemprop="articleBody">
<div class="section" id="d-wave-integration">
<h1>D-Wave Integration<a class="headerlink" href="#d-wave-integration" title="Permalink to this headline"></a></h1>
<div class="section" id="installation">
<h2>Installation<a class="headerlink" href="#installation" title="Permalink to this headline"></a></h2>
<div class="admonition note">
<p class="first admonition-title">Note</p>
<p>If you want support for the D-Wave Accelerator, you must install
<a class="reference external" href="https://github.com/microsoft/cpprestsdk">CppRestSDK</a> and OpenSSL. This
is required for these Accelerators to make remote HTTP Rest calls to their
respective server APIs. Here’s how to install these as binaries on various popular platforms:</p>
<div class="code last highlight-default"><div class="highlight"><pre><span></span>$ (macosx) brew install cpprestsdk
$ (fedora) dnf install cpprest-devel openssl-devel
$ (ubuntu) apt-get install libcpprest-dev libssl-dev
</pre></div>
</div>
</div>
<p>The <a class="reference external" href="https://github.com/ornl-qci/xacc-dwave">D-Wave Plugin</a> provides
support to XACC for executing programs on the D-Wave QPU via the D-Wave Accelerator.</p>
<p>To install this plugin, run the following</p>
<div class="code highlight-default"><div class="highlight"><pre><span></span>$ xacc-install-plugins.py -p xacc-dwave
</pre></div>
</div>
<p>You have now installed the D-Wave plugin. It is located in <code class="docutils literal"><span class="pre">$XACC_ROOT/lib/plugins/accelerator</span></code> and <code class="docutils literal"><span class="pre">$XACC_ROOT/lib/plugins/compilers</span></code>, where XACC_ROOT is your XACC install prefix.</p>
<div class="section" id="extensibility-for-minor-graph-embedding-algorithms">
<h3>Extensibility for Minor Graph Embedding Algorithms<a class="headerlink" href="#extensibility-for-minor-graph-embedding-algorithms" title="Permalink to this headline"></a></h3>
<p>XACC has extensibility built in for minor graph embedding
algorithms. We currently have one supported embedding algorithm (with more coming online), a wrapper around the D-Wave SAPI Cai, Macready, Roi algorithm. In order to install this as a plugin, run the following</p>
<div class="admonition note">
<p class="first admonition-title">Note</p>
<p class="last">The following embedding algorithm needs to leverage the proprietary
D-Wave SAPI header file and associated shared library: <code class="docutils literal"><span class="pre">dwave_sapi.h</span></code> and <code class="docutils literal"><span class="pre">libdwave_sapi.so</span></code> (or <code class="docutils literal"><span class="pre">libdwave_sapi.dylib</span></code> on macosx).
In order for the installation below to work, place dwave_sapi.h in <code class="docutils literal"><span class="pre">/usr/local/include/</span></code> and <code class="docutils literal"><span class="pre">libdwave_sapi.so</span></code> or <code class="docutils literal"><span class="pre">libdwave_sapi.dylib</span></code> in <code class="docutils literal"><span class="pre">/usr/local/lib/</span></code></p>
</div>
<div class="code highlight-default"><div class="highlight"><pre><span></span>$ xacc-install-plugins.py -p xacc-dwave-sapi-embedding
</pre></div>
</div>
<p>You have now installed the D-Wave plugin. It is located in <code cla