ViennaCL - The Vienna Computing Library
1.5.0
|
00001 #ifndef VIENNACL_SCHEDULER_EXECUTE_SCALAR_ASSIGN_HPP 00002 #define VIENNACL_SCHEDULER_EXECUTE_SCALAR_ASSIGN_HPP 00003 00004 /* ========================================================================= 00005 Copyright (c) 2010-2013, Institute for Microelectronics, 00006 Institute for Analysis and Scientific Computing, 00007 TU Wien. 00008 Portions of this software are copyright by UChicago Argonne, LLC. 00009 00010 ----------------- 00011 ViennaCL - The Vienna Computing Library 00012 ----------------- 00013 00014 Project Head: Karl Rupp rupp@iue.tuwien.ac.at 00015 00016 (A list of authors and contributors can be found in the PDF manual) 00017 00018 License: MIT (X11), see file LICENSE in the base directory 00019 ============================================================================= */ 00020 00021 00026 #include "viennacl/forwards.h" 00027 #include "viennacl/scheduler/forwards.h" 00028 #include "viennacl/scheduler/execute_vector_dispatcher.hpp" 00029 00030 namespace viennacl 00031 { 00032 namespace scheduler 00033 { 00035 inline void execute_scalar_assign_composite(statement const & s, statement_node const & root_node) 00036 { 00037 statement_node const & leaf = s.array()[root_node.rhs.node_index]; 00038 00039 if (leaf.op.type == OPERATION_BINARY_INNER_PROD_TYPE) // alpha = inner_prod( (x), (y) ) with x, y being either vectors or expressions 00040 { 00041 assert(root_node.lhs.type_family == SCALAR_TYPE_FAMILY && bool("Inner product requires assignment to scalar type!")); 00042 00043 if ( leaf.lhs.type_family == VECTOR_TYPE_FAMILY 00044 && leaf.rhs.type_family == VECTOR_TYPE_FAMILY) 00045 00046 { 00047 detail::inner_prod_impl(leaf.lhs, leaf.rhs, root_node.lhs); 00048 } 00049 else if ( leaf.lhs.type_family == COMPOSITE_OPERATION_FAMILY // temporary for (x) 00050 && leaf.rhs.type_family == VECTOR_TYPE_FAMILY) 00051 { 00052 statement_node new_root_x; 00053 00054 detail::new_element(new_root_x.lhs, leaf.rhs); 00055 00056 new_root_x.op.type_family = OPERATION_BINARY_TYPE_FAMILY; 00057 new_root_x.op.type = OPERATION_BINARY_ASSIGN_TYPE; 00058 00059 new_root_x.rhs.type_family = COMPOSITE_OPERATION_FAMILY; 00060 new_root_x.rhs.subtype = INVALID_SUBTYPE; 00061 new_root_x.rhs.numeric_type = INVALID_NUMERIC_TYPE; 00062 new_root_x.rhs.node_index = leaf.lhs.node_index; 00063 00064 // work on subexpression: 00065 // TODO: Catch exception, free temporary, then rethrow 00066 detail::execute_composite(s, new_root_x); 00067 00068 detail::inner_prod_impl(new_root_x.lhs, leaf.rhs, root_node.lhs); 00069 00070 detail::delete_element(new_root_x.lhs); 00071 } 00072 else if ( leaf.lhs.type_family == VECTOR_TYPE_FAMILY 00073 && leaf.rhs.type_family == COMPOSITE_OPERATION_FAMILY) // temporary for (y) 00074 { 00075 statement_node new_root_y; 00076 00077 detail::new_element(new_root_y.lhs, leaf.lhs); 00078 00079 new_root_y.op.type_family = OPERATION_BINARY_TYPE_FAMILY; 00080 new_root_y.op.type = OPERATION_BINARY_ASSIGN_TYPE; 00081 00082 new_root_y.rhs.type_family = COMPOSITE_OPERATION_FAMILY; 00083 new_root_y.rhs.subtype = INVALID_SUBTYPE; 00084 new_root_y.rhs.numeric_type = INVALID_NUMERIC_TYPE; 00085 new_root_y.rhs.node_index = leaf.rhs.node_index; 00086 00087 // work on subexpression: 00088 // TODO: Catch exception, free temporary, then rethrow 00089 detail::execute_composite(s, new_root_y); 00090 00091 detail::inner_prod_impl(leaf.lhs, new_root_y.lhs, root_node.lhs); 00092 00093 detail::delete_element(new_root_y.lhs); 00094 } 00095 else if ( leaf.lhs.type_family == COMPOSITE_OPERATION_FAMILY // temporary for (x) 00096 && leaf.rhs.type_family == COMPOSITE_OPERATION_FAMILY) // temporary for (y) 00097 { 00098 // extract size information from vectors: 00099 lhs_rhs_element const & temp_node = detail::extract_representative_vector(s, leaf.lhs); 00100 00101 // temporary for (x) 00102 statement_node new_root_x; 00103 detail::new_element(new_root_x.lhs, temp_node); 00104 00105 new_root_x.op.type_family = OPERATION_BINARY_TYPE_FAMILY; 00106 new_root_x.op.type = OPERATION_BINARY_ASSIGN_TYPE; 00107 00108 new_root_x.rhs.type_family = COMPOSITE_OPERATION_FAMILY; 00109 new_root_x.rhs.subtype = INVALID_SUBTYPE; 00110 new_root_x.rhs.numeric_type = INVALID_NUMERIC_TYPE; 00111 new_root_x.rhs.node_index = leaf.lhs.node_index; 00112 00113 // work on subexpression: 00114 // TODO: Catch exception, free temporary, then rethrow 00115 detail::execute_composite(s, new_root_x); 00116 00117 // temporary for (y) 00118 statement_node new_root_y; 00119 detail::new_element(new_root_y.lhs, temp_node); 00120 00121 new_root_y.op.type_family = OPERATION_BINARY_TYPE_FAMILY; 00122 new_root_y.op.type = OPERATION_BINARY_ASSIGN_TYPE; 00123 00124 new_root_y.rhs.type_family = COMPOSITE_OPERATION_FAMILY; 00125 new_root_y.rhs.subtype = INVALID_SUBTYPE; 00126 new_root_y.rhs.numeric_type = INVALID_NUMERIC_TYPE; 00127 new_root_y.rhs.node_index = leaf.rhs.node_index; 00128 00129 // work on subexpression: 00130 // TODO: Catch exception, free temporary, then rethrow 00131 detail::execute_composite(s, new_root_y); 00132 00133 // compute inner product: 00134 detail::inner_prod_impl(new_root_x.lhs, new_root_y.lhs, root_node.lhs); 00135 00136 detail::delete_element(new_root_x.lhs); 00137 detail::delete_element(new_root_y.lhs); 00138 } 00139 else 00140 throw statement_not_supported_exception("Cannot deal with inner product of the provided arguments"); 00141 } 00142 else if ( leaf.op.type == OPERATION_UNARY_NORM_1_TYPE 00143 || leaf.op.type == OPERATION_UNARY_NORM_2_TYPE 00144 || leaf.op.type == OPERATION_UNARY_NORM_INF_TYPE) 00145 { 00146 assert(root_node.lhs.type_family == SCALAR_TYPE_FAMILY && bool("Inner product requires assignment to scalar type!")); 00147 00148 if (leaf.lhs.type_family == VECTOR_TYPE_FAMILY) 00149 { 00150 detail::norm_impl(leaf.lhs, root_node.lhs, leaf.op.type); 00151 } 00152 else if (leaf.lhs.type_family == COMPOSITE_OPERATION_FAMILY) //introduce temporary: 00153 { 00154 lhs_rhs_element const & temp_node = detail::extract_representative_vector(s, leaf.lhs); 00155 00156 statement_node new_root_y; 00157 00158 detail::new_element(new_root_y.lhs, temp_node); 00159 00160 new_root_y.op.type_family = OPERATION_BINARY_TYPE_FAMILY; 00161 new_root_y.op.type = OPERATION_BINARY_ASSIGN_TYPE; 00162 00163 new_root_y.rhs.type_family = COMPOSITE_OPERATION_FAMILY; 00164 new_root_y.rhs.subtype = INVALID_SUBTYPE; 00165 new_root_y.rhs.numeric_type = INVALID_NUMERIC_TYPE; 00166 new_root_y.rhs.node_index = leaf.lhs.node_index; 00167 00168 // work on subexpression: 00169 // TODO: Catch exception, free temporary, then rethrow 00170 detail::execute_composite(s, new_root_y); 00171 00172 detail::norm_impl(new_root_y.lhs, root_node.lhs, leaf.op.type); 00173 00174 detail::delete_element(new_root_y.lhs); 00175 } 00176 else 00177 throw statement_not_supported_exception("Cannot deal with norm_inf of the provided arguments"); 00178 } 00179 else 00180 throw statement_not_supported_exception("Unsupported operation for scalar."); 00181 } 00182 00183 00184 } 00185 00186 } //namespace viennacl 00187 00188 #endif 00189