diff options
Diffstat (limited to 'src/boost/libs/numeric/ublas/benchmarks/opencl')
8 files changed, 752 insertions, 0 deletions
diff --git a/src/boost/libs/numeric/ublas/benchmarks/opencl/Jamfile b/src/boost/libs/numeric/ublas/benchmarks/opencl/Jamfile new file mode 100644 index 00000000..670ec66b --- /dev/null +++ b/src/boost/libs/numeric/ublas/benchmarks/opencl/Jamfile @@ -0,0 +1,27 @@ +# +# Copyright (c) 2018 Stefan Seefeld +# +# Distributed under the Boost Software License, Version 1.0. +# (See accompanying file LICENSE_1_0.txt or +# copy at http://www.boost.org/LICENSE_1_0.txt) + +import ac ; + +# work around a bug in Boost.Build +import ../../opencl ; +import ../../clblas ; +using opencl ; +using clblas ; + +project boost/ublas/benchmarks/opencl + : requirements + <library>/boost/program_options//boost_program_options + <toolset>gcc:<cxxflags>-Wno-ignored-attributes + [ ac.check-library /clblas//clblas : <library>/clblas//clblas <library>/opencl//opencl : <build>no ] + ; + +exe add : add.cpp ; +exe mm_prod : mm_prod.cpp ; +exe mv_prod : mv_prod.cpp ; +exe inner_prod : inner_prod.cpp ; +exe outer_prod : outer_prod.cpp ; diff --git a/src/boost/libs/numeric/ublas/benchmarks/opencl/add.cpp b/src/boost/libs/numeric/ublas/benchmarks/opencl/add.cpp new file mode 100644 index 00000000..b998cd2c --- /dev/null +++ b/src/boost/libs/numeric/ublas/benchmarks/opencl/add.cpp @@ -0,0 +1,93 @@ +// +// Copyright (c) 2018 Stefan Seefeld +// +// Distributed under the Boost Software License, Version 1.0. +// (See accompanying file LICENSE_1_0.txt or +// copy at http://www.boost.org/LICENSE_1_0.txt) + +#define BOOST_UBLAS_ENABLE_OPENCL +#include <boost/numeric/ublas/opencl.hpp> +#include <boost/program_options.hpp> +#include "benchmark.hpp" +#include <complex> +#include <string> + +namespace po = boost::program_options; +namespace ublas = boost::numeric::ublas; +namespace bm = boost::numeric::ublas::benchmark; +namespace opencl = boost::numeric::ublas::opencl; + +namespace boost { namespace numeric { namespace ublas { namespace benchmark { namespace opencl { + +template <typename S, bool C> class add; + +template <typename V, bool C> +class add<void(V,V,V), C> : public benchmark<void(V,V,V), C> +{ +public: + add(std::string const &name) : benchmark<void(V,V,V), C>(name) {} + virtual void operation(long l) + { + ublas::opencl::element_add(*this->a, *this->b, *this->c, this->queue); + } +}; + +}}}}} + +template <typename T> +void benchmark(std::string const &type, bool copy) +{ + using vector = ublas::vector<T>; + std::string name = "opencl::elementwise_add(vector<" + type + ">)"; + std::vector<long> sizes({1, 2, 4, 8, 16, 32, 64, 128, 256, 512, 1024, 2048, 4096}); + if (copy) + { + bm::opencl::add<void(vector, vector, vector), true> p(name); + p.run(sizes); + } + else + { + bm::opencl::add<void(vector, vector, vector), false> p(name); + p.run(sizes); + } +} + +int main(int argc, char **argv) +{ + opencl::library lib; + po::variables_map vm; + try + { + po::options_description desc("Matrix-vector product (OpenCL)\n" + "Allowed options"); + desc.add_options()("help,h", "produce help message"); + desc.add_options()("type,t", po::value<std::string>(), "select value-type (float, double, fcomplex, dcomplex)"); + desc.add_options()("copy,c", po::value<bool>(), "include host<->device copy in timing"); + + po::store(po::parse_command_line(argc, argv, desc), vm); + po::notify(vm); + + if (vm.count("help")) + { + std::cout << desc << std::endl; + return 0; + } + } + catch(std::exception &e) + { + std::cerr << "error: " << e.what() << std::endl; + return 1; + } + std::string type = vm.count("type") ? vm["type"].as<std::string>() : "float"; + bool copy = vm.count("copy") ? vm["copy"].as<bool>() : false; + if (type == "float") + benchmark<float>("float", copy); + else if (type == "double") + benchmark<double>("double", copy); + else if (type == "fcomplex") + benchmark<std::complex<float>>("std::complex<float>", copy); + else if (type == "dcomplex") + benchmark<std::complex<double>>("std::complex<double>", copy); + else + std::cerr << "unsupported value-type \"" << vm["type"].as<std::string>() << '\"' << std::endl; +} diff --git a/src/boost/libs/numeric/ublas/benchmarks/opencl/benchmark.hpp b/src/boost/libs/numeric/ublas/benchmarks/opencl/benchmark.hpp new file mode 100644 index 00000000..fb607599 --- /dev/null +++ b/src/boost/libs/numeric/ublas/benchmarks/opencl/benchmark.hpp @@ -0,0 +1,214 @@ +// +// Copyright (c) 2018 Stefan Seefeld +// +// Distributed under the Boost Software License, Version 1.0. +// (See accompanying file LICENSE_1_0.txt or +// copy at http://www.boost.org/LICENSE_1_0.txt) + +#ifndef opencl_benchmark_hpp_ +#define opencl_benchmark_hpp_ +#define BOOST_UBLAS_ENABLE_OPENCL + +#include <boost/numeric/ublas/opencl.hpp> +#include "../benchmark.hpp" +#include "init.hpp" +#include <memory> + +namespace boost { namespace numeric { namespace ublas { namespace benchmark { +namespace opencl { + +struct base +{ + base(compute::device d = compute::system::default_device()) + : context(d), + queue(context, d) + {} + compute::context context; + compute::command_queue queue; +}; + +template <typename T, bool C> struct data_factory; +template <typename T> +struct data_factory<T, true> +{ + typedef T type; + typedef std::unique_ptr<type> ptr_type; + static ptr_type create(long) { return ptr_type(new T());} +}; +template <typename T> +struct data_factory<T, false> +{ + typedef T type; + typedef std::unique_ptr<type> ptr_type; + static ptr_type create(long, compute::context) { return ptr_type(new T());} +}; +template <> +struct data_factory<void, true> +{ + typedef void type; + typedef void *ptr_type; + static ptr_type create(long) { return 0;} +}; +template <> +struct data_factory<void, false> +{ + typedef void type; + typedef void *ptr_type; + static ptr_type create(long, compute::context) { return 0;} +}; +template <typename T> +struct data_factory<ublas::vector<T>, true> +{ + typedef ublas::vector<T> type; + typedef std::unique_ptr<type> ptr_type; + static ptr_type create(long l) { return ptr_type(new type(l));} +}; +template <typename T> +struct data_factory<ublas::vector<T>, false> +{ + typedef ublas::vector<T, ublas::opencl::storage> type; + typedef std::unique_ptr<type> ptr_type; + static ptr_type create(long l, compute::context c) + { return ptr_type(new type(l, c));} +}; +template <typename T, typename L> +struct data_factory<ublas::matrix<T, L>, true> +{ + typedef ublas::matrix<T, L> type; + typedef std::unique_ptr<type> ptr_type; + static ptr_type create(long l) + { return ptr_type(new type(l, l));} +}; +template <typename T, typename L> +struct data_factory<ublas::matrix<T, L>, false> +{ + typedef ublas::matrix<T, L, ublas::opencl::storage> type; + typedef std::unique_ptr<type> ptr_type; + static ptr_type create(long l, compute::context c) + { return ptr_type(new type(l, l, c));} +}; + +template <typename S, bool> class benchmark; + +template <typename R, typename O> +class benchmark<R(O), true> : public base, public ublas::benchmark::benchmark +{ +public: + benchmark(std::string const &name) + : base(), + ublas::benchmark::benchmark(name + " with copy") + {} + virtual void setup(long l) + { + r = data_factory<R, true>::create(l); + a = data_factory<O, true>::create(l); + init(*a, l, 200); + } + typename data_factory<R, true>::ptr_type r; + typename data_factory<O, true>::ptr_type a; +}; + +template <typename R, typename O1, typename O2> +class benchmark<R(O1, O2), true> : public base, public ublas::benchmark::benchmark +{ +public: + benchmark(std::string const &name) + : base(), + ublas::benchmark::benchmark(name + " with copy") + {} + virtual void setup(long l) + { + r = data_factory<R, true>::create(l); + a = data_factory<O1, true>::create(l); + init(*a, l, 200); + b = data_factory<O2, true>::create(l); + init(*b, l, 200); + } + typename data_factory<R, true>::ptr_type r; + typename data_factory<O1, true>::ptr_type a; + typename data_factory<O2, true>::ptr_type b; +}; + +template <typename R, typename O1, typename O2, typename O3> +class benchmark<R(O1, O2, O3), true> : public base, public ublas::benchmark::benchmark +{ +public: + benchmark(std::string const &name) + : base(), + ublas::benchmark::benchmark(name + " with copy") + {} + virtual void setup(long l) + { + r = data_factory<R, true>::create(l); + a = data_factory<O1, true>::create(l); + init(*a, l, 200); + b = data_factory<O2, true>::create(l); + init(*b, l, 200); + c = data_factory<O3, true>::create(l); + init(*c, l, 200); + } + typename data_factory<R, true>::ptr_type r; + typename data_factory<O1, true>::ptr_type a; + typename data_factory<O2, true>::ptr_type b; + typename data_factory<O3, true>::ptr_type c; +}; + +template <typename R, typename O> +class benchmark<R(O), false> : public base, public ublas::benchmark::benchmark +{ +public: + benchmark(std::string const &name) + : base(), + ublas::benchmark::benchmark(name + " w/o copy") + {} + virtual void setup(long l) + { + r = data_factory<R, false>::create(l, context); + a = data_factory<O, false>::create(l, context); + init(*a, l, 200); + } + typename data_factory<R, false>::ptr_type r; + typename data_factory<O, false>::ptr_type a; +}; + +template <typename R, typename O1, typename O2> +class benchmark<R(O1, O2), false> : public base, public ublas::benchmark::benchmark +{ +public: + benchmark(std::string const &name) : base(), ublas::benchmark::benchmark(name + " w/o copy") {} + virtual void setup(long l) + { + r = data_factory<R, false>::create(l, context); + a = data_factory<O1, false>::create(l, context); + init(*a, l, 200); + b = data_factory<O2, false>::create(l, context); + init(*b, l, 200); + } + typename data_factory<R, false>::ptr_type r; + typename data_factory<O1, false>::ptr_type a; + typename data_factory<O2, false>::ptr_type b; +}; + +template <typename R, typename O1, typename O2, typename O3> +class benchmark<R(O1, O2, O3), false> : public base, public ublas::benchmark::benchmark +{ +public: + benchmark(std::string const &name) : base(), ublas::benchmark::benchmark(name + " w/o copy") {} + virtual void setup(long l) + { + r = data_factory<R, false>::create(l, context); + a = data_factory<O1, false>::create(l, context); + init(*a, l, 200); + b = data_factory<O2, false>::create(l, context); + init(*b, l, 200); + c = data_factory<O3, false>::create(l, context); + init(*c, l, 200); + } + typename data_factory<R, false>::ptr_type r; + typename data_factory<O1, false>::ptr_type a; + typename data_factory<O2, false>::ptr_type b; + typename data_factory<O3, false>::ptr_type c; +}; +}}}}} + +#endif diff --git a/src/boost/libs/numeric/ublas/benchmarks/opencl/init.hpp b/src/boost/libs/numeric/ublas/benchmarks/opencl/init.hpp new file mode 100644 index 00000000..a1141028 --- /dev/null +++ b/src/boost/libs/numeric/ublas/benchmarks/opencl/init.hpp @@ -0,0 +1,40 @@ +// +// Copyright (c) 2018 Stefan Seefeld +// All rights reserved. +// +// This file is part of Boost.uBLAS. It is made available under the +// Boost Software License, Version 1.0. +// (Consult LICENSE or http://www.boost.org/LICENSE_1_0.txt) + +#pragma once + +#include <boost/numeric/ublas/opencl.hpp> +#include "../init.hpp" + +namespace boost { namespace numeric { namespace ublas { namespace benchmark { + +template <typename T> +void init(T &v, unsigned long size, int max_value) +{ + // TBD +} + +template <typename T> +void init(vector<T, opencl::storage> &v, unsigned long size, int max_value) +{ + // TBD +} + +template <typename T> +void init(matrix<T, opencl::storage> &m, unsigned long size1, unsigned long size2, int max_value) +{ + // TBD +} + +template <typename T> +void init(matrix<T, opencl::storage> &m, unsigned long size, int max_value) +{ + init(m, size, size, max_value); +} + +}}}} diff --git a/src/boost/libs/numeric/ublas/benchmarks/opencl/inner_prod.cpp b/src/boost/libs/numeric/ublas/benchmarks/opencl/inner_prod.cpp new file mode 100644 index 00000000..a25664cb --- /dev/null +++ b/src/boost/libs/numeric/ublas/benchmarks/opencl/inner_prod.cpp @@ -0,0 +1,94 @@ +// +// Copyright (c) 2018 Stefan Seefeld +// All rights reserved. +// +// This file is part of Boost.uBLAS. It is made available under the +// Boost Software License, Version 1.0. +// (Consult LICENSE or http://www.boost.org/LICENSE_1_0.txt) + +#define BOOST_UBLAS_ENABLE_OPENCL +#include <boost/numeric/ublas/opencl.hpp> +#include <boost/program_options.hpp> +#include "benchmark.hpp" +#include <complex> +#include <string> + +namespace po = boost::program_options; +namespace ublas = boost::numeric::ublas; +namespace bm = boost::numeric::ublas::benchmark; +namespace opencl = boost::numeric::ublas::opencl; + +namespace boost { namespace numeric { namespace ublas { namespace benchmark { namespace opencl { + +template <typename S, bool C> class inner_prod; + +template <typename R, typename V, bool C> +class inner_prod<R(V,V), C> : public benchmark<R(V,V), C> +{ +public: + inner_prod(std::string const &name) : benchmark<R(V,V), C>(name) {} + virtual void operation(long l) + { + ublas::opencl::inner_prod(*this->a, *this->b, this->queue); + } +}; + +}}}}} + +template <typename T> +void benchmark(std::string const &type, bool copy) +{ + using vector = ublas::vector<T>; + std::string name = "opencl::inner_prod(vector<" + type + ">)"; + std::vector<long> sizes({1, 2, 4, 8, 16, 32, 64, 128, 256, 512, 1024, 2048, 4096, 8192, 16384, 32768, 65536}); + if (copy) + { + bm::opencl::inner_prod<T(vector,vector), true> p(name); + p.run(sizes); + } + else + { + bm::opencl::inner_prod<T(vector,vector), false> p(name); + p.run(sizes); + } +} + +int main(int argc, char **argv) +{ + opencl::library lib; + po::variables_map vm; + try + { + po::options_description desc("Inner product\n" + "Allowed options"); + desc.add_options()("help,h", "produce help message"); + desc.add_options()("type,t", po::value<std::string>(), "select value-type (float, double, fcomplex, dcomplex)"); + desc.add_options()("copy,c", po::value<bool>(), "include host<->device copy in timing"); + + po::store(po::parse_command_line(argc, argv, desc), vm); + po::notify(vm); + + if (vm.count("help")) + { + std::cout << desc << std::endl; + return 0; + } + } + catch(std::exception &e) + { + std::cerr << "error: " << e.what() << std::endl; + return 1; + } + std::string type = vm.count("type") ? vm["type"].as<std::string>() : "float"; + bool copy = vm.count("copy") ? vm["copy"].as<bool>() : false; + if (type == "float") + benchmark<float>("float", copy); + else if (type == "double") + benchmark<double>("double", copy); + // else if (type == "fcomplex") + // benchmark<std::complex<float>>("std::complex<float>", copy); + // else if (type == "dcomplex") + // benchmark<std::complex<double>>("std::complex<double>", copy); + else + std::cerr << "unsupported value-type \"" << vm["type"].as<std::string>() << '\"' << std::endl; +} diff --git a/src/boost/libs/numeric/ublas/benchmarks/opencl/mm_prod.cpp b/src/boost/libs/numeric/ublas/benchmarks/opencl/mm_prod.cpp new file mode 100644 index 00000000..e306031f --- /dev/null +++ b/src/boost/libs/numeric/ublas/benchmarks/opencl/mm_prod.cpp @@ -0,0 +1,94 @@ +// +// Copyright (c) 2018 Stefan Seefeld +// All rights reserved. +// +// This file is part of Boost.uBLAS. It is made available under the +// Boost Software License, Version 1.0. +// (Consult LICENSE or http://www.boost.org/LICENSE_1_0.txt) + +#define BOOST_UBLAS_ENABLE_OPENCL +#include <boost/numeric/ublas/opencl.hpp> +#include <boost/program_options.hpp> +#include "benchmark.hpp" +#include <complex> +#include <string> + +namespace po = boost::program_options; +namespace ublas = boost::numeric::ublas; +namespace bm = boost::numeric::ublas::benchmark; +namespace opencl = boost::numeric::ublas::opencl; + +namespace boost { namespace numeric { namespace ublas { namespace benchmark { namespace opencl { + +template <typename S, bool C> class prod; + +template <typename M, bool C> +class prod<void(M,M,M), C> : public benchmark<void(M,M,M), C> +{ +public: + prod(std::string const &name) : benchmark<void(M,M,M), C>(name) {} + virtual void operation(long l) + { + ublas::opencl::prod(*this->a, *this->b, *this->c, this->queue); + } +}; + +}}}}} + +template <typename T> +void benchmark(std::string const &type, bool copy) +{ + using matrix = ublas::matrix<T>; + std::string name = "opencl::prod(matrix<" + type + ">)"; + std::vector<long> sizes({1, 2, 4, 8, 16, 32, 64, 128, 256, 512, 1024, 2048, 4096}); + if (copy) + { + bm::opencl::prod<void(matrix, matrix, matrix), true> p(name); + p.run(sizes); + } + else + { + bm::opencl::prod<void(matrix, matrix, matrix), false> p(name); + p.run(sizes); + } +} + +int main(int argc, char **argv) +{ + opencl::library lib; + po::variables_map vm; + try + { + po::options_description desc("Matrix product (OpenCL)\n" + "Allowed options"); + desc.add_options()("help,h", "produce help message"); + desc.add_options()("type,t", po::value<std::string>(), "select value-type (float, double, fcomplex, dcomplex)"); + desc.add_options()("copy,c", po::value<bool>(), "include host<->device copy in timing"); + + po::store(po::parse_command_line(argc, argv, desc), vm); + po::notify(vm); + + if (vm.count("help")) + { + std::cout << desc << std::endl; + return 0; + } + } + catch(std::exception &e) + { + std::cerr << "error: " << e.what() << std::endl; + return 1; + } + std::string type = vm.count("type") ? vm["type"].as<std::string>() : "float"; + bool copy = vm.count("copy") ? vm["copy"].as<bool>() : false; + if (type == "float") + benchmark<float>("float", copy); + else if (type == "double") + benchmark<double>("double", copy); + else if (type == "fcomplex") + benchmark<std::complex<float>>("std::complex<float>", copy); + else if (type == "dcomplex") + benchmark<std::complex<double>>("std::complex<double>", copy); + else + std::cerr << "unsupported value-type \"" << vm["type"].as<std::string>() << '\"' << std::endl; +} diff --git a/src/boost/libs/numeric/ublas/benchmarks/opencl/mv_prod.cpp b/src/boost/libs/numeric/ublas/benchmarks/opencl/mv_prod.cpp new file mode 100644 index 00000000..70344a4b --- /dev/null +++ b/src/boost/libs/numeric/ublas/benchmarks/opencl/mv_prod.cpp @@ -0,0 +1,95 @@ +// +// Copyright (c) 2018 Stefan Seefeld +// All rights reserved. +// +// This file is part of Boost.uBLAS. It is made available under the +// Boost Software License, Version 1.0. +// (Consult LICENSE or http://www.boost.org/LICENSE_1_0.txt) + +#define BOOST_UBLAS_ENABLE_OPENCL +#include <boost/numeric/ublas/opencl.hpp> +#include <boost/program_options.hpp> +#include "benchmark.hpp" +#include <complex> +#include <string> + +namespace po = boost::program_options; +namespace ublas = boost::numeric::ublas; +namespace bm = boost::numeric::ublas::benchmark; +namespace opencl = boost::numeric::ublas::opencl; + +namespace boost { namespace numeric { namespace ublas { namespace benchmark { namespace opencl { + +template <typename S, bool C> class prod; + +template <typename M, typename V, bool C> +class prod<void(M,V,V), C> : public benchmark<void(M,V,V), C> +{ +public: + prod(std::string const &name) : benchmark<void(M,V,V), C>(name) {} + virtual void operation(long l) + { + ublas::opencl::prod(*this->a, *this->b, *this->c, this->queue); + } +}; + +}}}}} + +template <typename T> +void benchmark(std::string const &type, bool copy) +{ + using vector = ublas::vector<T>; + using matrix = ublas::matrix<T>; + std::string name = "opencl::prod(matrix<" + type + ", vector<" + type + ">)"; + std::vector<long> sizes({1, 2, 4, 8, 16, 32, 64, 128, 256, 512, 1024, 2048, 4096}); + if (copy) + { + bm::opencl::prod<void(matrix, vector, vector), true> p(name); + p.run(sizes); + } + else + { + bm::opencl::prod<void(matrix, vector, vector), false> p(name); + p.run(sizes); + } +} + +int main(int argc, char **argv) +{ + opencl::library lib; + po::variables_map vm; + try + { + po::options_description desc("Matrix-vector product (OpenCL)\n" + "Allowed options"); + desc.add_options()("help,h", "produce help message"); + desc.add_options()("type,t", po::value<std::string>(), "select value-type (float, double, fcomplex, dcomplex)"); + desc.add_options()("copy,c", po::value<bool>(), "include host<->device copy in timing"); + + po::store(po::parse_command_line(argc, argv, desc), vm); + po::notify(vm); + + if (vm.count("help")) + { + std::cout << desc << std::endl; + return 0; + } + } + catch(std::exception &e) + { + std::cerr << "error: " << e.what() << std::endl; + return 1; + } + std::string type = vm.count("type") ? vm["type"].as<std::string>() : "float"; + bool copy = vm.count("copy") ? vm["copy"].as<bool>() : false; + if (type == "float") + benchmark<float>("float", copy); + else if (type == "double") + benchmark<double>("double", copy); + else if (type == "fcomplex") + benchmark<std::complex<float>>("std::complex<float>", copy); + else if (type == "dcomplex") + benchmark<std::complex<double>>("std::complex<double>", copy); + else + std::cerr << "unsupported value-type \"" << vm["type"].as<std::string>() << '\"' << std::endl; +} diff --git a/src/boost/libs/numeric/ublas/benchmarks/opencl/outer_prod.cpp b/src/boost/libs/numeric/ublas/benchmarks/opencl/outer_prod.cpp new file mode 100644 index 00000000..b00bb840 --- /dev/null +++ b/src/boost/libs/numeric/ublas/benchmarks/opencl/outer_prod.cpp @@ -0,0 +1,95 @@ +// +// Copyright (c) 2018 Stefan Seefeld +// All rights reserved. +// +// This file is part of Boost.uBLAS. It is made available under the +// Boost Software License, Version 1.0. +// (Consult LICENSE or http://www.boost.org/LICENSE_1_0.txt) + +#define BOOST_UBLAS_ENABLE_OPENCL +#include <boost/numeric/ublas/opencl.hpp> +#include <boost/program_options.hpp> +#include "benchmark.hpp" +#include <complex> +#include <string> + +namespace po = boost::program_options; +namespace ublas = boost::numeric::ublas; +namespace bm = boost::numeric::ublas::benchmark; +namespace opencl = boost::numeric::ublas::opencl; + +namespace boost { namespace numeric { namespace ublas { namespace benchmark { namespace opencl { + +template <typename S, bool C> class outer_prod; + +template <typename V, typename M, bool C> +class outer_prod<void(V,V,M), C> : public benchmark<void(V,V,M), C> +{ +public: + outer_prod(std::string const &name) : benchmark<void(V,V,M), C>(name) {} + virtual void operation(long l) + { + ublas::opencl::outer_prod(*this->a, *this->b, *this->c, this->queue); + } +}; + +}}}}} + +template <typename T> +void benchmark(std::string const &type, bool copy) +{ + using vector = ublas::vector<T>; + using matrix = ublas::matrix<T>; + std::string name = "opencl::outer_prod(vector<" + type + ">)"; + std::vector<long> sizes({1, 2, 4, 8, 16, 32, 64, 128, 256, 512, 1024, 2048, 4096}); + if (copy) + { + bm::opencl::outer_prod<void(vector, vector, matrix), true> p(name); + p.run(sizes); + } + else + { + bm::opencl::outer_prod<void(vector, vector, matrix), false> p(name); + p.run(sizes); + } +} + +int main(int argc, char **argv) +{ + opencl::library lib; + po::variables_map vm; + try + { + po::options_description desc("Outer product\n" + "Allowed options"); + desc.add_options()("help,h", "produce help message"); + desc.add_options()("type,t", po::value<std::string>(), "select value-type (float, double, fcomplex, dcomplex)"); + desc.add_options()("copy,c", po::value<bool>(), "include host<->device copy in timing"); + + po::store(po::parse_command_line(argc, argv, desc), vm); + po::notify(vm); + + if (vm.count("help")) + { + std::cout << desc << std::endl; + return 0; + } + } + catch(std::exception &e) + { + std::cerr << "error: " << e.what() << std::endl; + return 1; + } + std::string type = vm.count("type") ? vm["type"].as<std::string>() : "float"; + bool copy = vm.count("copy") ? vm["copy"].as<bool>() : false; + if (type == "float") + benchmark<float>("float", copy); + else if (type == "double") + benchmark<double>("double", copy); + else if (type == "fcomplex") + benchmark<std::complex<float>>("std::complex<float>", copy); + else if (type == "dcomplex") + benchmark<std::complex<double>>("std::complex<double>", copy); + else + std::cerr << "unsupported value-type \"" << vm["type"].as<std::string>() << '\"' << std::endl; +} |