1 /**********************************************************************************************/
2 /* This program is part of the Barcelona OpenMP Tasks Suite */
3 /* Copyright (C) 2009 Barcelona Supercomputing Center - Centro Nacional de Supercomputacion */
4 /* Copyright (C) 2009 Universitat Politecnica de Catalunya */
5 /* */
6 /* This program is free software; you can redistribute it and/or modify */
7 /* it under the terms of the GNU General Public License as published by */
8 /* the Free Software Foundation; either version 2 of the License, or */
9 /* (at your option) any later version. */
10 /* */
11 /* This program is distributed in the hope that it will be useful, */
12 /* but WITHOUT ANY WARRANTY; without even the implied warranty of */
13 /* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the */
14 /* GNU General Public License for more details. */
15 /* */
16 /* You should have received a copy of the GNU General Public License */
17 /* along with this program; if not, write to the Free Software */
18 /* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA */
19 /**********************************************************************************************/
20
21 /***********************************************************************
22 * main function & common behaviour of the benchmark.
23 **********************************************************************/
24 #include <CLI11.hpp>
25 #include "strassen.hpp"
26
strassen_alg(const std::string & model,const unsigned num_threads,const unsigned num_rounds)27 void strassen_alg(
28 const std::string& model,
29 const unsigned num_threads,
30 const unsigned num_rounds
31 ) {
32
33 std::cout << std::setw(12) << "runtime"
34 << std::endl;
35
36 double runtime {0.0};
37
38 for(unsigned j=0; j<num_rounds; ++j) {
39 if(model == "tf") {
40 runtime += measure_time_taskflow(num_threads, MatrixA, MatrixB, MatrixC, MATRIX_SIZE).count();
41 }
42 else if(model == "tbb") {
43 runtime += measure_time_tbb(num_threads, MatrixA, MatrixB, MatrixC, MATRIX_SIZE).count();
44 }
45 else if(model == "omp") {
46 runtime += measure_time_omp(num_threads, MatrixA, MatrixB, MatrixC, MATRIX_SIZE).count();
47 }
48 else assert(false);
49 }
50
51 std::cout << std::setw(12) << runtime / num_rounds / 1e3
52 << std::endl;
53 }
54
55
56
57
58 /***********************************************************************
59 * main:
60 **********************************************************************/
main(int argc,char * argv[])61 int main(int argc, char* argv[]) {
62 CLI::App app{"Strassen algorithm for matrix multiplication"};
63
64 unsigned num_threads {1};
65 app.add_option("-t,--num_threads", num_threads, "number of threads (default=1)");
66
67 unsigned num_rounds {1};
68 app.add_option("-r,--num_rounds", num_rounds, "number of rounds (default=1)");
69
70 bool check_result {false};
71 app.add_option("-c,--check", check_result, "compare result with sequential mode (default=false)");
72
73 std::string model = "tf";
74 app.add_option("-m,--model", model, "model name tbb|omp|tf (default=tf)")
75 ->check([] (const std::string& m) {
76 if(m != "tbb" && m != "tf" && m != "omp") {
77 return "model name should be \"tbb\", \"omp\", or \"tf\"";
78 }
79 return "";
80 });
81
82 CLI11_PARSE(app, argc, argv);
83
84 std::cout << "model=" << model << ' '
85 << "num_threads=" << num_threads << ' '
86 << "num_rounds=" << num_rounds << ' '
87 << "check result=" << check_result << ' '
88 << std::endl;
89
90
91 init_ABC();
92
93 strassen_alg(model, num_threads, num_rounds);
94
95 if(check_result) {
96 // Compare against the sequential matrix multiplication
97 double *D;
98 D = alloc_matrix(MATRIX_SIZE);
99 auto beg = std::chrono::high_resolution_clock::now();
100 //OptimizedStrassenMultiply_seq(D, MatrixA, MatrixB, MATRIX_SIZE, MATRIX_SIZE, MATRIX_SIZE, MATRIX_SIZE, 1);
101 auto end = std::chrono::high_resolution_clock::now();
102 std::cout << "Seq: " << std::chrono::duration_cast<std::chrono::microseconds>(end - beg).count()/1e3 << std::endl;
103 matrixmul(MATRIX_SIZE, MatrixA, MATRIX_SIZE, MatrixB, MATRIX_SIZE, D, MATRIX_SIZE);
104 assert(compare_matrix(MATRIX_SIZE, MatrixC, MATRIX_SIZE, D, MATRIX_SIZE) == 1);
105 std::cout << "Correct!\n";
106 free(D);
107 }
108
109 free(MatrixA);
110 free(MatrixB);
111 free(MatrixC);
112
113 return 0;
114 }
115
116