ViennaCL - The Vienna Computing Library
1.5.0
|
00001 #ifndef VIENNACL_BACKEND_MEM_HANDLE_HPP 00002 #define VIENNACL_BACKEND_MEM_HANDLE_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 00025 #include <vector> 00026 #include <cassert> 00027 #include "viennacl/forwards.h" 00028 #include "viennacl/tools/shared_ptr.hpp" 00029 #include "viennacl/backend/cpu_ram.hpp" 00030 00031 #ifdef VIENNACL_WITH_OPENCL 00032 #include "viennacl/backend/opencl.hpp" 00033 #endif 00034 00035 #ifdef VIENNACL_WITH_CUDA 00036 #include "viennacl/backend/cuda.hpp" 00037 #endif 00038 00039 00040 namespace viennacl 00041 { 00042 namespace backend 00043 { 00044 00045 00046 // if a user compiles with CUDA, it is reasonable to expect that CUDA should be the default 00047 #ifdef VIENNACL_WITH_CUDA 00048 inline memory_types default_memory_type() { return CUDA_MEMORY; } 00049 #elif defined(VIENNACL_WITH_OPENCL) 00050 inline memory_types default_memory_type() { return OPENCL_MEMORY; } 00051 #else 00052 inline memory_types default_memory_type() { return MAIN_MEMORY; } 00053 #endif 00054 00055 00062 class mem_handle 00063 { 00064 public: 00065 typedef viennacl::tools::shared_ptr<char> ram_handle_type; 00066 typedef viennacl::tools::shared_ptr<char> cuda_handle_type; 00067 00069 mem_handle() : active_handle_(MEMORY_NOT_INITIALIZED), size_in_bytes_(0) {} 00070 00072 ram_handle_type & ram_handle() { return ram_handle_; } 00074 ram_handle_type const & ram_handle() const { return ram_handle_; } 00075 00076 #ifdef VIENNACL_WITH_OPENCL 00077 00078 viennacl::ocl::handle<cl_mem> & opencl_handle() { return opencl_handle_; } 00080 viennacl::ocl::handle<cl_mem> const & opencl_handle() const { return opencl_handle_; } 00081 #endif 00082 00083 #ifdef VIENNACL_WITH_CUDA 00084 00085 cuda_handle_type & cuda_handle() { return cuda_handle_; } 00087 cuda_handle_type const & cuda_handle() const { return cuda_handle_; } 00088 #endif 00089 00091 memory_types get_active_handle_id() const { return active_handle_; } 00092 00094 void switch_active_handle_id(memory_types new_id) 00095 { 00096 if (new_id != active_handle_) 00097 { 00098 if (active_handle_ == MEMORY_NOT_INITIALIZED) 00099 active_handle_ = new_id; 00100 else if (active_handle_ == MAIN_MEMORY) 00101 { 00102 active_handle_ = new_id; 00103 } 00104 else if (active_handle_ == OPENCL_MEMORY) 00105 { 00106 #ifdef VIENNACL_WITH_OPENCL 00107 active_handle_ = new_id; 00108 #else 00109 throw "compiled without OpenCL suppport!"; 00110 #endif 00111 } 00112 else if (active_handle_ == CUDA_MEMORY) 00113 { 00114 #ifdef VIENNACL_WITH_CUDA 00115 active_handle_ = new_id; 00116 #else 00117 throw "compiled without CUDA suppport!"; 00118 #endif 00119 } 00120 else 00121 throw "invalid new memory region!"; 00122 } 00123 } 00124 00126 bool operator==(mem_handle const & other) const 00127 { 00128 if (active_handle_ != other.active_handle_) 00129 return false; 00130 00131 switch (active_handle_) 00132 { 00133 case MAIN_MEMORY: 00134 return ram_handle_.get() == other.ram_handle_.get(); 00135 #ifdef VIENNACL_WITH_OPENCL 00136 case OPENCL_MEMORY: 00137 return opencl_handle_.get() == other.opencl_handle_.get(); 00138 #endif 00139 #ifdef VIENNACL_WITH_CUDA 00140 case CUDA_MEMORY: 00141 return cuda_handle_.get() == other.cuda_handle_.get(); 00142 #endif 00143 default: break; 00144 } 00145 00146 return false; 00147 } 00148 00152 bool operator<(mem_handle const & other) const 00153 { 00154 if (active_handle_ != other.active_handle_) 00155 return false; 00156 00157 switch (active_handle_) 00158 { 00159 case MAIN_MEMORY: 00160 return ram_handle_.get() < other.ram_handle_.get(); 00161 #ifdef VIENNACL_WITH_OPENCL 00162 case OPENCL_MEMORY: 00163 return opencl_handle_.get() < other.opencl_handle_.get(); 00164 #endif 00165 #ifdef VIENNACL_WITH_CUDA 00166 case CUDA_MEMORY: 00167 return cuda_handle_.get() < other.cuda_handle_.get(); 00168 #endif 00169 default: break; 00170 } 00171 00172 return false; 00173 } 00174 00175 00176 bool operator!=(mem_handle const & other) const { return !(*this == other); } 00177 00179 void swap(mem_handle & other) 00180 { 00181 // swap handle type: 00182 memory_types active_handle_tmp = other.active_handle_; 00183 other.active_handle_ = active_handle_; 00184 active_handle_ = active_handle_tmp; 00185 00186 // swap ram handle: 00187 ram_handle_type ram_handle_tmp = other.ram_handle_; 00188 other.ram_handle_ = ram_handle_; 00189 ram_handle_ = ram_handle_tmp; 00190 00191 // swap OpenCL handle: 00192 #ifdef VIENNACL_WITH_OPENCL 00193 opencl_handle_.swap(other.opencl_handle_); 00194 #endif 00195 #ifdef VIENNACL_WITH_CUDA 00196 cuda_handle_type cuda_handle_tmp = other.cuda_handle_; 00197 other.cuda_handle_ = cuda_handle_; 00198 cuda_handle_ = cuda_handle_tmp; 00199 #endif 00200 } 00201 00203 vcl_size_t raw_size() const { return size_in_bytes_; } 00204 00206 void raw_size(vcl_size_t new_size) { size_in_bytes_ = new_size; } 00207 00208 private: 00209 memory_types active_handle_; 00210 ram_handle_type ram_handle_; 00211 #ifdef VIENNACL_WITH_OPENCL 00212 viennacl::ocl::handle<cl_mem> opencl_handle_; 00213 #endif 00214 #ifdef VIENNACL_WITH_CUDA 00215 cuda_handle_type cuda_handle_; 00216 #endif 00217 vcl_size_t size_in_bytes_; 00218 }; 00219 00220 00221 } //backend 00222 00223 00224 } //viennacl 00225 #endif