diff --git a/src/shogun/base/init.cpp b/src/shogun/base/init.cpp index 2803c069445..1976fdb374e 100644 --- a/src/shogun/base/init.cpp +++ b/src/shogun/base/init.cpp @@ -14,6 +14,7 @@ #include #include +#include #include #include #include @@ -37,6 +38,9 @@ namespace shogun Version* sg_version=NULL; CMath* sg_math=NULL; CRandom* sg_rand=NULL; +#ifdef HAVE_CXX11 + std::unique_ptr sg_linalg(nullptr); +#endif /// function called to print normal messages void (*sg_print_message)(FILE* target, const char* str) = NULL; @@ -66,6 +70,10 @@ namespace shogun sg_math = new shogun::CMath(); if (!sg_rand) sg_rand = new shogun::CRandom(); +#ifdef HAVE_CXX11 + if (!sg_linalg) + sg_linalg = std::unique_ptr(new shogun::SGLinalg()); +#endif #ifdef TRACE_MEMORY_ALLOCS if (!sg_mallocs) sg_mallocs = new shogun::CMap(631, 1024, false); @@ -186,6 +194,13 @@ namespace shogun return sg_rand; } +#ifdef HAVE_CXX11 + SGLinalg* get_global_linalg() + { + return sg_linalg.get(); + } +#endif + void init_from_env() { char* env_log_val = NULL; diff --git a/src/shogun/base/init.h b/src/shogun/base/init.h index 793fc881b79..980eb586f45 100644 --- a/src/shogun/base/init.h +++ b/src/shogun/base/init.h @@ -22,6 +22,7 @@ namespace shogun class Version; class Parallel; class CRandom; + class SGLinalg; /** This function must be called before libshogun is used. Usually shogun does * not provide any output messages (neither debugging nor error; apart from @@ -108,6 +109,18 @@ void set_global_rand(CRandom* rand); */ CRandom* get_global_rand(); +/** set the global linalg library object + * + * @param linalg linalg object to use + */ +void set_global_linlg(SGLinalg* linalg); + +/** get the global linalg library object + * + * @return linalg object + */ +SGLinalg* get_global_linlg(); + /** Checks environment variables and modifies global objects */ void init_from_env(); diff --git a/src/shogun/mathematics/linalg/BaseVector.h b/src/shogun/mathematics/linalg/BaseVector.h new file mode 100644 index 00000000000..9c0015f995f --- /dev/null +++ b/src/shogun/mathematics/linalg/BaseVector.h @@ -0,0 +1,63 @@ +/* + * Copyright (c) 2016, Shogun-Toolbox e.V. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, + * this list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * 3. Neither the name of the copyright holder nor the names of its + * contributors may be used to endorse or promote products derived from + * this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + * + * Authors: 2016 Pan Deng, Soumyajit De, Viktor Gal + */ + +#include +#include + +#ifndef BASEVECTOR_H__ +#define BASEVECTOR_H__ + +#ifdef HAVE_CXX11 + +namespace shogun +{ + +/** Vector structure + * Base vector for both CPU and GPU vector + */ +template +struct BaseVector +{ + /** Default Constructor */ + BaseVector() + { + } + + /** Data Storage */ + virtual bool onGPU() = 0 ; +}; +} + +#endif // HAVE_CXX11 + +#endif diff --git a/src/shogun/mathematics/linalg/CPUBackend.cpp b/src/shogun/mathematics/linalg/CPUBackend.cpp new file mode 100644 index 00000000000..c1ddcf9b8f3 --- /dev/null +++ b/src/shogun/mathematics/linalg/CPUBackend.cpp @@ -0,0 +1,63 @@ +/* + * Copyright (c) 2016, Shogun-Toolbox e.V. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, + * this list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * 3. Neither the name of the copyright holder nor the names of its + * contributors may be used to endorse or promote products derived from + * this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + * + * Authors: 2016 Pan Deng, Soumyajit De, Viktor Gal + */ + +#include + +#ifdef HAVE_CXX11 + +namespace shogun +{ + +CPUBackend::CPUBackend() +{ +} + +CPUBackend::CPUBackend(const CPUBackend& cpubackend) +{ +} + +template +T CPUBackend::dot(const CPUVector &a, const CPUVector &b) const +{ + typedef Eigen::Matrix VectorXt; + Eigen::Map vec_a(a.CPUptr, a.vlen); + Eigen::Map vec_b(b.CPUptr, b.vlen); + return vec_a.dot(vec_b); +} + +template int32_t CPUBackend::dot(const CPUVector &a, const CPUVector &b) const; +template float32_t CPUBackend::dot(const CPUVector &a, const CPUVector &b) const; + +} + +#endif //HAVE_CXX11 diff --git a/src/shogun/mathematics/linalg/CPUBackend.h b/src/shogun/mathematics/linalg/CPUBackend.h new file mode 100644 index 00000000000..ce85ccc75db --- /dev/null +++ b/src/shogun/mathematics/linalg/CPUBackend.h @@ -0,0 +1,74 @@ +/* + * Copyright (c) 2016, Shogun-Toolbox e.V. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, + * this list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * 3. Neither the name of the copyright holder nor the names of its + * contributors may be used to endorse or promote products derived from + * this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + * + * Authors: 2016 Pan Deng, Soumyajit De, Viktor Gal + */ + +#include +#include +#include + +#ifndef CPUBACKEND_H__ +#define CPUBACKEND_H__ + +#ifdef HAVE_CXX11 + +namespace shogun +{ + +/** CPU Backend Class */ +class CPUBackend +{ +public: + + /** Default Constructor */ + CPUBackend(); + + /** Copy constructor */ + CPUBackend(const CPUBackend& cpubackend); + + /** + * Implementation of Eigen3 vector dot-product that works + * with CPUVectors (SGVectors) + * + * @param a first vector + * @param b second vector + * @return the dot product of \f$\mathbf{a}\f$ and \f$\mathbf{b}\f$, represented + * as \f$\sum_i a_i b_i\f$ + */ + template + T dot(const CPUVector &a, const CPUVector &b) const; +}; + +} + +#endif //HAVE_CXX11 + +#endif diff --git a/src/shogun/mathematics/linalg/CPUVector.cpp b/src/shogun/mathematics/linalg/CPUVector.cpp new file mode 100644 index 00000000000..8a6e74db4ec --- /dev/null +++ b/src/shogun/mathematics/linalg/CPUVector.cpp @@ -0,0 +1,63 @@ +/* + * Copyright (c) 2016, Shogun-Toolbox e.V. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, + * this list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * 3. Neither the name of the copyright holder nor the names of its + * contributors may be used to endorse or promote products derived from + * this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + * + * Authors: 2016 Pan Deng, Soumyajit De, Viktor Gal + */ + +#include + +#ifdef HAVE_CXX11 + +namespace shogun + +{ +template +CPUVector::CPUVector():CPUptr(nullptr), vlen(0) +{ +} + +template +CPUVector::CPUVector(const SGVector &vector) +: CPUptr(vector.vector), vlen(vector.vlen) +{ +} + +template +CPUVector::CPUVector(const CPUVector &vector) +: CPUptr(vector.CPUptr), vlen(vector.vlen) +{ +} + +template struct CPUVector; +template struct CPUVector; + +} + +#endif //HAVE_CXX11 diff --git a/src/shogun/mathematics/linalg/CPUVector.h b/src/shogun/mathematics/linalg/CPUVector.h new file mode 100644 index 00000000000..18a4a1b7250 --- /dev/null +++ b/src/shogun/mathematics/linalg/CPUVector.h @@ -0,0 +1,75 @@ +/* + * Copyright (c) 2016, Shogun-Toolbox e.V. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, + * this list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * 3. Neither the name of the copyright holder nor the names of its + * contributors may be used to endorse or promote products derived from + * this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + * + * Authors: 2016 Pan Deng, Soumyajit De, Viktor Gal + */ + +#include +#include +#include + +#ifndef CPUVECTOR_H__ +#define CPUVECTOR_H__ + +#ifdef HAVE_CXX11 + +namespace shogun +{ + +/** CPU vector structure */ +template +struct CPUVector : public BaseVector +{ + /** vector */ + T* CPUptr; + /** length of vector */ + index_t vlen; + + /** Default Constructor */ + CPUVector(); + + /** Wrap SGVector */ + CPUVector(const SGVector &vector); + + /** Copy Constructor*/ + CPUVector(const CPUVector &vector); + + /** Data Storage */ + inline bool onGPU() + { + return false; + } +}; + +} + +#endif //HAVE_CXX11 + +#endif diff --git a/src/shogun/mathematics/linalg/GPUArray.cpp b/src/shogun/mathematics/linalg/GPUArray.cpp new file mode 100644 index 00000000000..d95c3b90454 --- /dev/null +++ b/src/shogun/mathematics/linalg/GPUArray.cpp @@ -0,0 +1,89 @@ +/* + * Copyright (c) 2016, Shogun-Toolbox e.V. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, + * this list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * 3. Neither the name of the copyright holder nor the names of its + * contributors may be used to endorse or promote products derived from + * this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + * + * Authors: 2016 Pan Deng, Soumyajit De, Viktor Gal + */ + +#include + +#ifdef HAVE_CXX11 + +namespace shogun +{ + +#ifdef HAVE_VIENNACL + +template +GPUVector::GPUArray::GPUArray(const SGVector &vector) +:GPUptr(new VCLMemoryArray()), vlen(vector.vlen), offset(0) +{ + viennacl::backend::memory_create(*GPUptr, sizeof(T)*vlen, + viennacl::context()); + + viennacl::backend::memory_write(*GPUptr, 0, vlen*sizeof(T), + vector.vector); +} + +template +GPUVector::GPUArray::GPUArray(const GPUVector::GPUArray &array) +{ + GPUptr = array.GPUptr; + vlen = array.vlen; + offset = array.offset; +} + +template +typename GPUVector::GPUArray::VCLVectorBase GPUVector::GPUArray::GPUvec() +{ + return VCLVectorBase(*GPUptr, vlen, offset, 1); +} + +template +typename GPUVector::GPUArray::VCLVector GPUVector::GPUArray::vector() +{ + return VCLVector(GPUVector::GPUArray::GPUvec()); +} + +#else // HAVE_VIENNACL + +template +GPUVector::GPUArray::GPUArray(const SGVector &vector) +{ + SG_SERROR("User did not register GPU backend. \n"); +} + +#endif //HAVE_VIENNACL + +template struct GPUVector; +template struct GPUVector; + +} + +#endif //HAVE_CXX11 diff --git a/src/shogun/mathematics/linalg/GPUArray.h b/src/shogun/mathematics/linalg/GPUArray.h new file mode 100644 index 00000000000..f60db90ab76 --- /dev/null +++ b/src/shogun/mathematics/linalg/GPUArray.h @@ -0,0 +1,100 @@ +/* + * Copyright (c) 2016, Shogun-Toolbox e.V. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, + * this list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * 3. Neither the name of the copyright holder nor the names of its + * contributors may be used to endorse or promote products derived from + * this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + * + * Authors: 2016 Pan Deng, Soumyajit De, Viktor Gal + */ + +#include +#include +#include +#include +#include + +#ifdef HAVE_VIENNACL +#include +#endif + +#ifndef GPU_ARRAY_H__ +#define GPU_ARRAY_H__ + +#ifdef HAVE_CXX11 + +namespace shogun +{ + +/** GPU array structure */ +template +struct GPUVector::GPUArray +{ + +#ifdef HAVE_VIENNACL + typedef viennacl::backend::mem_handle VCLMemoryArray; + typedef viennacl::vector_base VCLVectorBase; + typedef viennacl::vector VCLVector; + + /** Memory segment holding the data for the vector */ + std::shared_ptr GPUptr; + + /** Vector length */ + index_t vlen; + + /** Offset for the memory segment, i.e the data of the vector + * starts at vector+offset + */ + index_t offset; + + /** Creates a gpu vector with SGVector */ + GPUArray(const SGVector &vector); + + /** Copy Constructor */ + GPUArray(const GPUVector::GPUArray &array); + + /** Returns a ViennaCL vector wrapped around the data of this vector. Can be + * used to call native ViennaCL methods on this vector + */ + VCLVectorBase GPUvec(); + + /** Cast of VCLVectorBase to VCLVector + * allows element access + */ + VCLVector vector(); + +#else //HAVE_VIENNACL + /** Creates a gpu vector with SGVector */ + GPUArray(const SGVector &vector); +#endif //HAVE_VIENNACL + +}; + +} + +#endif //HAVE_CXX11 + +#endif diff --git a/src/shogun/mathematics/linalg/GPUBackend.cpp b/src/shogun/mathematics/linalg/GPUBackend.cpp new file mode 100644 index 00000000000..e3ceb81271a --- /dev/null +++ b/src/shogun/mathematics/linalg/GPUBackend.cpp @@ -0,0 +1,68 @@ +/* + * Copyright (c) 2016, Shogun-Toolbox e.V. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, + * this list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * 3. Neither the name of the copyright holder nor the names of its + * contributors may be used to endorse or promote products derived from + * this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + * + * Authors: 2016 Pan Deng, Soumyajit De, Viktor Gal + */ + +#include +#include + +#ifdef HAVE_VIENNACL +#include +#include +#endif + +#ifdef HAVE_CXX11 + +namespace shogun +{ + +GPUBackend::GPUBackend() +{ +} + +template +T GPUBackend::dot(const GPUVector &a, const GPUVector &b) const +{ +#ifdef HAVE_VIENNACL + return viennacl::linalg::inner_prod(a.gpuarray->GPUvec(), b.gpuarray->GPUvec()); + +#else + SG_SERROR("User did not register GPU backend. \n"); + return T(0); +#endif +} + +template int32_t GPUBackend::dot(const GPUVector &a, const GPUVector &b) const; +template float32_t GPUBackend::dot(const GPUVector &a, const GPUVector &b) const; + +} + +#endif //HAVE_CXX11 diff --git a/src/shogun/mathematics/linalg/GPUBackend.h b/src/shogun/mathematics/linalg/GPUBackend.h new file mode 100644 index 00000000000..8db17bd4f39 --- /dev/null +++ b/src/shogun/mathematics/linalg/GPUBackend.h @@ -0,0 +1,75 @@ +/* + * Copyright (c) 2016, Shogun-Toolbox e.V. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, + * this list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * 3. Neither the name of the copyright holder nor the names of its + * contributors may be used to endorse or promote products derived from + * this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + * + * Authors: 2016 Pan Deng, Soumyajit De, Viktor Gal + */ + +#include +#include +#include +#include +#include +#include +#include + +#ifndef GPUBACKEND_H__ +#define GPUBACKEND_H__ + +#ifdef HAVE_CXX11 + +namespace shogun +{ + +/** GPU backend */ +class GPUBackend +{ +public: + /** Default Constructor */ + GPUBackend(); + + /** + * Implementation of vector dot-product that works + * with GPUVectors + * Works with different GPU algebra libraries + * + * @param a first vector + * @param b second vector + * @return the dot product of \f$\mathbf{a}\f$ and \f$\mathbf{b}\f$, represented + * as \f$\sum_i a_i b_i\f$ + */ + template + T dot(const GPUVector &a, const GPUVector &b) const; +}; + +} + +#endif //HAVE_CXX11 + +#endif diff --git a/src/shogun/mathematics/linalg/GPUVector.cpp b/src/shogun/mathematics/linalg/GPUVector.cpp new file mode 100644 index 00000000000..0ba7ff4470b --- /dev/null +++ b/src/shogun/mathematics/linalg/GPUVector.cpp @@ -0,0 +1,106 @@ +/* + * Copyright (c) 2016, Shogun-Toolbox e.V. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, + * this list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * 3. Neither the name of the copyright holder nor the names of its + * contributors may be used to endorse or promote products derived from + * this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + * + * Authors: 2016 Pan Deng, Soumyajit De, Viktor Gal + */ + +#include +#include + +#ifdef HAVE_CXX11 + +namespace shogun +{ + +template +GPUVector::GPUVector() +{ + init(); +} + +template +GPUVector::GPUVector(const SGVector &vector) +{ + init(); + vlen = vector.vlen; + +#ifdef HAVE_VIENNACL + gpuarray = std::unique_ptr(new GPUArray(vector)); +#else + SG_SERROR("User did not register GPU backend. \n"); +#endif +} + +template +GPUVector::GPUVector(const GPUVector &vector) +{ + init(); + vlen = vector.vlen; + offset = vector.offset; +#ifdef HAVE_VIENNACL + gpuarray = std::unique_ptr(new GPUArray(*(vector.gpuarray))); +#else + SG_SERROR("User did not register GPU backend. \n"); +#endif +} + +template +void GPUVector::init() +{ + vlen = 0; + offset = 0; +} + +template +GPUVector& GPUVector::operator=(const GPUVector &other) +{ + // check for self-assignment + if(&other == this) + { + return *this; + } + + // reuse storage when possible + gpuarray.reset(new GPUArray(*(other.gpuarray))); + vlen = other.vlen; + return *this; +} + +template +GPUVector::~GPUVector() +{ +} + +template struct GPUVector; +template struct GPUVector; + +} + +#endif //HAVE_CXX11 diff --git a/src/shogun/mathematics/linalg/GPUVector.h b/src/shogun/mathematics/linalg/GPUVector.h new file mode 100644 index 00000000000..c7e67d8a782 --- /dev/null +++ b/src/shogun/mathematics/linalg/GPUVector.h @@ -0,0 +1,96 @@ +/* + * Copyright (c) 2016, Shogun-Toolbox e.V. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, + * this list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * 3. Neither the name of the copyright holder nor the names of its + * contributors may be used to endorse or promote products derived from + * this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + * + * Authors: 2016 Pan Deng, Soumyajit De, Viktor Gal + */ + +#include +#include +#include +#include +#include + +#ifndef GPU_Vector_H__ +#define GPU_Vector_H__ + +#ifdef HAVE_CXX11 + +namespace shogun +{ + +/** GPU vector wrapper structure */ +template +struct GPUVector : public BaseVector +{ + /** Structure for different types of GPU vectors */ + struct GPUArray; + + /** Opaque pointer of GPUArray */ + std::unique_ptr gpuarray; + + /** Default Constructor */ + GPUVector(); + + /** Wrap SGVector */ + GPUVector(const SGVector &vector); + + /** Copy Constructor*/ + GPUVector(const GPUVector &vector); + + /** Empty destructor */ + ~GPUVector(); + + /** needs to be overridden to initialize empty data */ + void init(); + + /** Overload operator "=" */ + GPUVector& operator=(const GPUVector &other); + + /** Data Storage */ + inline bool onGPU() + { + return true; + } + +public: + /** Vector length */ + index_t vlen; + + /** Offset for the memory segment, i.e the data of the vector + * starts at vector+offset + */ + index_t offset; +}; + +} + +#endif //HAVE_CXX11 + +#endif diff --git a/src/shogun/mathematics/linalg/SGLinalg.cpp b/src/shogun/mathematics/linalg/SGLinalg.cpp new file mode 100644 index 00000000000..89917ad477c --- /dev/null +++ b/src/shogun/mathematics/linalg/SGLinalg.cpp @@ -0,0 +1,125 @@ +/* + * Copyright (c) 2016, Shogun-Toolbox e.V. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, + * this list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * 3. Neither the name of the copyright holder nor the names of its + * contributors may be used to endorse or promote products derived from + * this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + * + * Authors: 2016 Pan Deng, Soumyajit De, Viktor Gal + */ + +#include + +#ifdef HAVE_CXX11 + +namespace shogun +{ + +SGLinalg::SGLinalg():m_cpubackend(std::shared_ptr(new CPUBackend)), m_gpubackend(nullptr) +{ +} + +SGLinalg::SGLinalg(std::shared_ptr cpubackend) +:m_cpubackend(cpubackend), m_gpubackend(nullptr) +{ +} + +SGLinalg::SGLinalg(std::shared_ptr gpubackend) +:m_cpubackend(std::shared_ptr(new CPUBackend)), m_gpubackend(gpubackend) + { + } + +SGLinalg::SGLinalg(std::shared_ptr cpubackend, std::shared_ptr gpubackend) +:m_cpubackend(cpubackend), m_gpubackend(gpubackend) + { + } + +void SGLinalg::set_cpu_backend(std::shared_ptr cpubackend) +{ + m_cpubackend = cpubackend; +} + +std::shared_ptr SGLinalg::get_cpu_backend() +{ + return m_cpubackend; +} + +void SGLinalg::set_gpu_backend(std::shared_ptr gpubackend) +{ + m_gpubackend = gpubackend; +} + +std::shared_ptr SGLinalg::get_gpu_backend() +{ + return m_gpubackend; +} + +template +T SGLinalg::dot(BaseVector *a, BaseVector *b) const +{ + if (a->onGPU() && b->onGPU()) + { + if (this->hasGPUBackend()) + { + // do the gpu backend dot product + // you shouldn't care whether it's viennacl or some other GPU backend. + return m_gpubackend->dot(static_cast&>(*a), + static_cast&>(*b)); + } + else + { + SG_SERROR("User did not register GPU backend. \n"); + return -1; + } + } + else + { + // take care that the matricies are on the same backend + if (a->onGPU()) + { + SG_SERROR("User did not register GPU backend. \n"); + return -1; + } + else if (b->onGPU()) + { + SG_SERROR("User did not register GPU backend. \n"); + return -1; + } + return m_cpubackend->dot(static_cast&>(*a), + static_cast&>(*b)); + } +} + +bool SGLinalg::hasGPUBackend() const +{ + return m_gpubackend != nullptr; +} + +template int32_t SGLinalg::dot(BaseVector *a, BaseVector *b) const; +template float32_t SGLinalg::dot(BaseVector *a, BaseVector *b) const; +} + +#endif //HAVE_CXX11 diff --git a/src/shogun/mathematics/linalg/SGLinalg.h b/src/shogun/mathematics/linalg/SGLinalg.h new file mode 100644 index 00000000000..24712994743 --- /dev/null +++ b/src/shogun/mathematics/linalg/SGLinalg.h @@ -0,0 +1,116 @@ +/* + * Copyright (c) 2016, Shogun-Toolbox e.V. + * All rights reserved. + * + * Redistribution and use in source and binary forms, with or without + * modification, are permitted provided that the following conditions are met: + * + * 1. Redistributions of source code must retain the above copyright notice, + * this list of conditions and the following disclaimer. + * + * 2. Redistributions in binary form must reproduce the above copyright + * notice, this list of conditions and the following disclaimer in the + * documentation and/or other materials provided with the distribution. + * + * 3. Neither the name of the copyright holder nor the names of its + * contributors may be used to endorse or promote products derived from + * this software without specific prior written permission. + * + * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" + * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE + * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE + * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE + * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR + * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF + * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS + * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN + * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) + * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE + * POSSIBILITY OF SUCH DAMAGE. + * + * Authors: 2016 Pan Deng, Soumyajit De, Viktor Gal + */ + +#include +#include +#include +#include +#include +#include +#include +#include + +#ifndef LINALGR_H__ +#define LINALGR_H__ + +#ifdef HAVE_CXX11 + +namespace shogun +{ + +/** Linalg Class **/ +class SGLinalg +{ + /** pointer to cpubackend */ + std::shared_ptr m_cpubackend; + + /** pointer to gpubackend */ + std::shared_ptr m_gpubackend; + +public: + /** Default Constructor */ + SGLinalg(); + + /** Constructor: explicitly set CPU Backend */ + SGLinalg(std::shared_ptr cpubackend); + + /** Constructor: explicitly set GPU Backend */ + SGLinalg(std::shared_ptr gpubackend); + + /** Constructor: explicitly set CPU and GPU Backend */ + SGLinalg(std::shared_ptr cpubackend, std::shared_ptr gpubackend); + + /** set CPU backend + * @param cpubackend cpubackend + */ + void set_cpu_backend(std::shared_ptr cpubackend); + + /** get CPU backend */ + std::shared_ptr get_cpu_backend(); + + /** set GPU backend + * @param gpubackend gpubackend + */ + void set_gpu_backend(std::shared_ptr gpubackend); + + /** get GPU backend */ + std::shared_ptr get_gpu_backend(); + + + /** + * Wrapper method of implementation of vector dot-product that works + * with generic vectors + * + * @param a first vector + * @param b second vector + * @return the dot product of \f$\mathbf{a}\f$ and \f$\mathbf{b}\f$, represented + * as \f$\sum_i a_i b_i\f$ + */ + template + T dot(BaseVector *a, BaseVector *b) const; + + /** Check whether gpubackend is registered by user */ + bool hasGPUBackend() const; + +}; + +} + +namespace shogun +{ + extern std::unique_ptr sg_linalg; +} + +#endif //HAVE_CXX11 + +#endif diff --git a/tests/unit/mathematics/SGLinalg_unittest.cc b/tests/unit/mathematics/SGLinalg_unittest.cc new file mode 100644 index 00000000000..7cd6c5db98c --- /dev/null +++ b/tests/unit/mathematics/SGLinalg_unittest.cc @@ -0,0 +1,111 @@ +/* + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 3 of the License, or + * (at your option) any later version. + * + * Written (W) 2016 Pan Deng + */ + +#include +#include +#include +#include +#include +#include + +using namespace shogun; + +#ifdef HAVE_CXX11 + +TEST(SGLinalg, CPU_Vector_convert) +{ + const index_t size = 10; + SGVector a(size); + for (index_t i = 0; i < size; ++i) + a[i] = i; + + CPUVector a_CPU(a); + + for (index_t i = 0; i < size; ++i) + EXPECT_NEAR(a[i], (a_CPU.CPUptr)[i], 1E-15); +} + +TEST(SGLinalg, CPU_Vector_copy) +{ + const index_t size = 10; + SGVector a(size); + for (index_t i = 0; i < size; ++i) + a[i] = i; + + CPUVector a_CPU(a); + CPUVector b_CPU(a_CPU); + + for (index_t i = 0; i < size; ++i) + EXPECT_NEAR((a_CPU.CPUptr)[i], (b_CPU.CPUptr)[i], 1E-15); +} + +TEST(SGLinalg, CPUBackend_dot) +{ + const index_t size=10; + SGVector a(size), b(size); + a.set_const(1); + b.set_const(2); + + CPUVector a_CPU(a); + CPUVector b_CPU(b); + + auto result = sg_linalg->dot(&a_CPU, &b_CPU); + + EXPECT_NEAR(result, 20.0, 1E-15); +} + +#ifdef HAVE_VIENNACL + +TEST(SGLinalg, GPU_Vector_convert) +{ + const index_t size = 10; + SGVector a(size); + for (index_t i = 0; i < size; ++i) + a[i] = i; + + GPUVector a_GPU(a); + + for (index_t i = 0; i < size; ++i) + EXPECT_NEAR(a[i], (a_GPU.gpuarray->vector())[i], 1E-15); +} + +TEST(SGLinalg, GPU_Vector_copy) +{ + const index_t size=10; + SGVector a(size), b(size); + for (index_t i = 0; i < size; ++i) + a[i] = i; + + GPUVector a_GPU(a); + GPUVector b_GPU; + b_GPU = a_GPU; +} + +TEST(SGLinalg, GPUBackend_dot) +{ + const index_t size=10; + SGVector a(size), b(size); + a.set_const(1); + b.set_const(2); + + GPUVector a_GPU(a); + GPUVector b_GPU(b); + + std::shared_ptr ViennaCLBackend; + ViennaCLBackend = std::shared_ptr(new GPUBackend); + + sg_linalg->set_gpu_backend(ViennaCLBackend); + auto result = sg_linalg->dot(&a_GPU, &b_GPU); + + EXPECT_NEAR(result, 20.0, 1E-15); +} + +#endif //HAVE_VIENNACL + +#endif //HAVE_CXX11