ViennaCL - The Vienna Computing Library  1.7.1
Free open-source GPU-accelerated linear algebra and solver library.
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Pages
execute_util.hpp
Go to the documentation of this file.
1 #ifndef VIENNACL_SCHEDULER_EXECUTE_UTIL_HPP
2 #define VIENNACL_SCHEDULER_EXECUTE_UTIL_HPP
3 
4 /* =========================================================================
5  Copyright (c) 2010-2016, Institute for Microelectronics,
6  Institute for Analysis and Scientific Computing,
7  TU Wien.
8  Portions of this software are copyright by UChicago Argonne, LLC.
9 
10  -----------------
11  ViennaCL - The Vienna Computing Library
12  -----------------
13 
14  Project Head: Karl Rupp rupp@iue.tuwien.ac.at
15 
16  (A list of authors and contributors can be found in the manual)
17 
18  License: MIT (X11), see file LICENSE in the base directory
19 ============================================================================= */
20 
21 
26 #include <assert.h>
27 
28 #include "viennacl/forwards.h"
29 #include "viennacl/scalar.hpp"
30 #include "viennacl/vector.hpp"
31 #include "viennacl/matrix.hpp"
33 
34 namespace viennacl
35 {
36 namespace scheduler
37 {
38 namespace detail
39 {
40 //
41 inline lhs_rhs_element const & extract_representative_vector(statement const & s, lhs_rhs_element const & element)
42 {
43  switch (element.type_family)
44  {
45  case VECTOR_TYPE_FAMILY:
46  return element;
48  {
49  statement_node const & leaf = s.array()[element.node_index];
50 
52  return extract_representative_vector(s, leaf.lhs);
53  switch (leaf.op.type)
54  {
62  return extract_representative_vector(s, leaf.lhs);
64  return extract_representative_vector(s, leaf.rhs);
65  default:
66  throw statement_not_supported_exception("Vector leaf encountered an invalid binary operation!");
67  }
68  }
69  default:
70  throw statement_not_supported_exception("Vector leaf encountered an invalid node type!");
71  }
72 }
73 
74 
75 // helper routines for extracting the scalar type
76 inline float convert_to_float(float f) { return f; }
77 inline float convert_to_float(double d) { return static_cast<float>(d); }
78 inline float convert_to_float(lhs_rhs_element const & el)
79 {
81  return el.host_float;
83  return *el.scalar_float;
84 
85  throw statement_not_supported_exception("Cannot convert to float");
86 }
87 
88 // helper routines for extracting the scalar type
89 inline double convert_to_double(float d) { return static_cast<double>(d); }
90 inline double convert_to_double(double d) { return d; }
91 inline double convert_to_double(lhs_rhs_element const & el)
92 {
94  return el.host_double;
96  return *el.scalar_double;
97 
98  throw statement_not_supported_exception("Cannot convert to double");
99 }
100 
106 {
107  if (root_node.lhs.type_family == SCALAR_TYPE_FAMILY)
108  {
109  switch (root_node.lhs.numeric_type)
110  {
111  case CHAR_TYPE:
112  return viennacl::traits::context(*root_node.lhs.scalar_char);
113  case UCHAR_TYPE:
114  return viennacl::traits::context(*root_node.lhs.scalar_char);
115  case SHORT_TYPE:
116  return viennacl::traits::context(*root_node.lhs.scalar_short);
117  case USHORT_TYPE:
118  return viennacl::traits::context(*root_node.lhs.scalar_ushort);
119  case INT_TYPE:
120  return viennacl::traits::context(*root_node.lhs.scalar_int);
121  case UINT_TYPE:
122  return viennacl::traits::context(*root_node.lhs.scalar_uint);
123  case LONG_TYPE:
124  return viennacl::traits::context(*root_node.lhs.scalar_long);
125  case ULONG_TYPE:
126  return viennacl::traits::context(*root_node.lhs.scalar_ulong);
127  //case HALF_TYPE:
128  //return viennacl::traits::context(*root_node.lhs.scalar_half);
129  case FLOAT_TYPE:
130  return viennacl::traits::context(*root_node.lhs.scalar_float);
131  case DOUBLE_TYPE:
132  return viennacl::traits::context(*root_node.lhs.scalar_double);
133  default:
134  throw statement_not_supported_exception("Invalid numeric type for extraction of context from scalar");
135  }
136  }
137  else if (root_node.lhs.type_family == VECTOR_TYPE_FAMILY)
138  {
139  switch (root_node.lhs.numeric_type)
140  {
141  case CHAR_TYPE:
142  return viennacl::traits::context(*root_node.lhs.vector_char);
143  case UCHAR_TYPE:
144  return viennacl::traits::context(*root_node.lhs.vector_char);
145  case SHORT_TYPE:
146  return viennacl::traits::context(*root_node.lhs.vector_short);
147  case USHORT_TYPE:
148  return viennacl::traits::context(*root_node.lhs.vector_ushort);
149  case INT_TYPE:
150  return viennacl::traits::context(*root_node.lhs.vector_int);
151  case UINT_TYPE:
152  return viennacl::traits::context(*root_node.lhs.vector_uint);
153  case LONG_TYPE:
154  return viennacl::traits::context(*root_node.lhs.vector_long);
155  case ULONG_TYPE:
156  return viennacl::traits::context(*root_node.lhs.vector_ulong);
157  //case HALF_TYPE:
158  //return viennacl::traits::context(*root_node.lhs.vector_half);
159  case FLOAT_TYPE:
160  return viennacl::traits::context(*root_node.lhs.vector_float);
161  case DOUBLE_TYPE:
162  return viennacl::traits::context(*root_node.lhs.vector_double);
163  default:
164  throw statement_not_supported_exception("Invalid numeric type for extraction of context from vector");
165  }
166  }
167  else if (root_node.lhs.type_family == MATRIX_TYPE_FAMILY)
168  {
169  switch (root_node.lhs.numeric_type)
170  {
171  case CHAR_TYPE:
172  return viennacl::traits::context(*root_node.lhs.matrix_char);
173  case UCHAR_TYPE:
174  return viennacl::traits::context(*root_node.lhs.matrix_char);
175  case SHORT_TYPE:
176  return viennacl::traits::context(*root_node.lhs.matrix_short);
177  case USHORT_TYPE:
178  return viennacl::traits::context(*root_node.lhs.matrix_ushort);
179  case INT_TYPE:
180  return viennacl::traits::context(*root_node.lhs.matrix_int);
181  case UINT_TYPE:
182  return viennacl::traits::context(*root_node.lhs.matrix_uint);
183  case LONG_TYPE:
184  return viennacl::traits::context(*root_node.lhs.matrix_long);
185  case ULONG_TYPE:
186  return viennacl::traits::context(*root_node.lhs.matrix_ulong);
187  //case HALF_TYPE:
188  //return viennacl::traits::context(*root_node.lhs.matrix_half);
189  case FLOAT_TYPE:
190  return viennacl::traits::context(*root_node.lhs.matrix_float);
191  case DOUBLE_TYPE:
192  return viennacl::traits::context(*root_node.lhs.matrix_double);
193  default:
194  throw statement_not_supported_exception("Invalid numeric type for extraction of context from matrix");
195  }
196  }
197 
198  throw statement_not_supported_exception("Invalid type for context extraction");
199 }
200 
201 
203 
204 inline void new_element(lhs_rhs_element & new_elem, lhs_rhs_element const & old_element, viennacl::context const & ctx)
205 {
206  new_elem.type_family = old_element.type_family;
207  new_elem.subtype = old_element.subtype;
208  new_elem.numeric_type = old_element.numeric_type;
209  if (new_elem.type_family == SCALAR_TYPE_FAMILY)
210  {
211  assert(new_elem.subtype == DEVICE_SCALAR_TYPE && bool("Expected a device scalar in root node"));
212 
213  switch (new_elem.numeric_type)
214  {
215  case FLOAT_TYPE:
216  new_elem.scalar_float = new viennacl::scalar<float>(0, ctx);
217  return;
218  case DOUBLE_TYPE:
219  new_elem.scalar_double = new viennacl::scalar<double>(0, ctx);
220  return;
221  default:
222  throw statement_not_supported_exception("Invalid vector type for vector construction");
223  }
224  }
225  else if (new_elem.type_family == VECTOR_TYPE_FAMILY)
226  {
227  assert(new_elem.subtype == DENSE_VECTOR_TYPE && bool("Expected a dense vector in root node"));
228 
229  switch (new_elem.numeric_type)
230  {
231  case FLOAT_TYPE:
232  new_elem.vector_float = new viennacl::vector<float>((old_element.vector_float)->size(), ctx);
233  return;
234  case DOUBLE_TYPE:
235  new_elem.vector_double = new viennacl::vector<double>((old_element.vector_float)->size(), ctx);
236  return;
237  default:
238  throw statement_not_supported_exception("Invalid vector type for vector construction");
239  }
240  }
241  else if (new_elem.type_family == MATRIX_TYPE_FAMILY)
242  {
243  assert( (new_elem.subtype == DENSE_MATRIX_TYPE) && bool("Expected a dense matrix in root node"));
244 
245  if (new_elem.subtype == DENSE_MATRIX_TYPE)
246  {
247  switch (new_elem.numeric_type)
248  {
249  case FLOAT_TYPE:
250  new_elem.matrix_float = new viennacl::matrix_base<float>((old_element.matrix_float)->size1(), (old_element.matrix_float)->size2(), (old_element.matrix_float)->row_major(), ctx);
251  return;
252  case DOUBLE_TYPE:
253  new_elem.matrix_double = new viennacl::matrix_base<double>((old_element.matrix_double)->size1(), (old_element.matrix_double)->size2(), (old_element.matrix_double)->row_major(), ctx);
254  return;
255  default:
256  throw statement_not_supported_exception("Invalid vector type for vector construction");
257  }
258  }
259  else
260  throw statement_not_supported_exception("Expected a dense matrix in root node when creating a temporary");
261  }
262  else
263  throw statement_not_supported_exception("Unknown type familty when creating new temporary object");
264 }
265 
266 inline void delete_element(lhs_rhs_element & elem)
267 {
268  if (elem.type_family == SCALAR_TYPE_FAMILY)
269  {
270  switch (elem.numeric_type)
271  {
272  case FLOAT_TYPE:
273  delete elem.scalar_float;
274  return;
275  case DOUBLE_TYPE:
276  delete elem.scalar_double;
277  return;
278  default:
279  throw statement_not_supported_exception("Invalid vector type for vector destruction");
280  }
281  }
282  else if (elem.type_family == VECTOR_TYPE_FAMILY)
283  {
284  switch (elem.numeric_type)
285  {
286  case FLOAT_TYPE:
287  delete elem.vector_float;
288  return;
289  case DOUBLE_TYPE:
290  delete elem.vector_double;
291  return;
292  default:
293  throw statement_not_supported_exception("Invalid vector type for vector destruction");
294  }
295  }
296  else if (elem.type_family == MATRIX_TYPE_FAMILY)
297  {
298  if (elem.subtype == DENSE_MATRIX_TYPE)
299  {
300  switch (elem.numeric_type)
301  {
302  case FLOAT_TYPE:
303  delete elem.matrix_float;
304  return;
305  case DOUBLE_TYPE:
306  delete elem.matrix_double;
307  return;
308  default:
309  throw statement_not_supported_exception("Invalid vector type for vector destruction");
310  }
311  }
312  else
313  throw statement_not_supported_exception("Expected a dense matrix in root node when deleting temporary");
314  }
315  else
316  throw statement_not_supported_exception("Unknown type familty when deleting temporary object");
317 }
318 
319 } // namespace detail
320 } // namespace scheduler
321 } // namespace viennacl
322 
323 #endif
324 
viennacl::scalar< float > * scalar_float
Definition: forwards.h:373
viennacl::vector_base< unsigned short > * vector_ushort
Definition: forwards.h:380
viennacl::vector_base< unsigned int > * vector_uint
Definition: forwards.h:382
viennacl::matrix_base< short > * matrix_short
Definition: forwards.h:403
viennacl::vector_base< short > * vector_short
Definition: forwards.h:379
viennacl::scalar< short > * scalar_short
Definition: forwards.h:367
Implementation of the dense matrix class.
viennacl::context extract_context(statement_node const &root_node)
Helper routine for extracting the context in which a statement is executed.
viennacl::matrix_base< char > * matrix_char
Definition: forwards.h:401
vcl_size_t size1(MatrixType const &mat)
Generic routine for obtaining the number of rows of a matrix (ViennaCL, uBLAS, etc.)
Definition: size.hpp:163
double convert_to_double(float d)
viennacl::vector_base< int > * vector_int
Definition: forwards.h:381
statement_node_subtype subtype
Definition: forwards.h:340
This file provides the forward declarations for the main types used within ViennaCL.
statement_node_type_family type_family
Definition: forwards.h:339
A class representing the 'data' for the LHS or RHS operand of the respective node.
Definition: forwards.h:337
container_type const & array() const
Definition: forwards.h:528
viennacl::scalar< unsigned int > * scalar_uint
Definition: forwards.h:370
viennacl::scalar< long > * scalar_long
Definition: forwards.h:371
operation_node_type_family type_family
Definition: forwards.h:473
result_of::size_type< MatrixType >::type size2(MatrixType const &mat)
Generic routine for obtaining the number of columns of a matrix (ViennaCL, uBLAS, etc...
Definition: size.hpp:201
viennacl::matrix_base< double > * matrix_double
Definition: forwards.h:410
void delete_element(lhs_rhs_element &elem)
Represents a generic 'context' similar to an OpenCL context, but is backend-agnostic and thus also su...
Definition: context.hpp:39
viennacl::scalar< unsigned long > * scalar_ulong
Definition: forwards.h:372
viennacl::matrix_base< long > * matrix_long
Definition: forwards.h:407
viennacl::matrix_base< unsigned short > * matrix_ushort
Definition: forwards.h:404
vcl_size_t size(VectorType const &vec)
Generic routine for obtaining the size of a vector (ViennaCL, uBLAS, etc.)
Definition: size.hpp:239
statement_node_numeric_type numeric_type
Definition: forwards.h:341
viennacl::vector_base< unsigned long > * vector_ulong
Definition: forwards.h:384
viennacl::vector_base< float > * vector_float
Definition: forwards.h:385
viennacl::matrix_base< float > * matrix_float
Definition: forwards.h:409
viennacl::vector_base< double > * vector_double
Definition: forwards.h:386
viennacl::matrix_base< unsigned long > * matrix_ulong
Definition: forwards.h:408
viennacl::scalar< double > * scalar_double
Definition: forwards.h:374
Provides the datastructures for dealing with a single statement such as 'x = y + z;'.
viennacl::scalar< unsigned short > * scalar_ushort
Definition: forwards.h:368
viennacl::vector_base< char > * vector_char
Definition: forwards.h:377
viennacl::context context(T const &t)
Returns an ID for the currently active memory domain of an object.
Definition: context.hpp:40
void new_element(lhs_rhs_element &new_elem, lhs_rhs_element const &old_element, viennacl::context const &ctx)
The vector type with operator-overloads and proxy classes is defined here. Linear algebra operations ...
bool row_major(T const &)
Definition: row_major.hpp:38
viennacl::scalar< int > * scalar_int
Definition: forwards.h:369
float convert_to_float(float f)
operation_node_type type
Definition: forwards.h:474
lhs_rhs_element const & extract_representative_vector(statement const &s, lhs_rhs_element const &element)
The main class for representing a statement such as x = inner_prod(y,z); at runtime.
Definition: forwards.h:502
viennacl::scalar< char > * scalar_char
Definition: forwards.h:365
viennacl::matrix_base< int > * matrix_int
Definition: forwards.h:405
Implementation of the ViennaCL scalar class.
viennacl::vector_base< long > * vector_long
Definition: forwards.h:383
Main datastructure for an node in the statement tree.
Definition: forwards.h:478
Exception for the case the scheduler is unable to deal with the operation.
Definition: forwards.h:38
viennacl::matrix_base< unsigned int > * matrix_uint
Definition: forwards.h:406