• Main Page
  • Namespaces
  • Data Structures
  • Files
  • File List
  • Globals

/data/development/ViennaCL/ViennaCL-1.1.2/viennacl/ocl/backend.hpp

Go to the documentation of this file.
00001 /* =======================================================================
00002    Copyright (c) 2010, Institute for Microelectronics, TU Vienna.
00003    http://www.iue.tuwien.ac.at
00004                              -----------------
00005                      ViennaCL - The Vienna Computing Library
00006                              -----------------
00007                             
00008    authors:    Karl Rupp                          rupp@iue.tuwien.ac.at
00009                Florian Rudolf                     flo.rudy+viennacl@gmail.com
00010                Josef Weinbub                      weinbub@iue.tuwien.ac.at
00011 
00012    license:    MIT (X11), see file LICENSE in the ViennaCL base directory
00013 ======================================================================= */
00014 
00015 #ifndef _VIENNACL_BACKEND_HPP_
00016 #define _VIENNACL_BACKEND_HPP_
00017 
00022 #include <vector>
00023 #include "viennacl/ocl/context.hpp"
00024 #include "viennacl/ocl/enqueue.hpp"
00025 
00026 namespace viennacl
00027 {
00028   namespace ocl
00029   {
00030     
00032     template <bool dummy = false>  //never use parameter other than default (introduced for linkage issues only)
00033     class backend
00034     {
00035       public:
00040         static void switch_context(long i)
00041         {
00042           current_context_id_ = i;
00043         }
00044         
00046         static viennacl::ocl::context & current_context()
00047         {
00048           if (!initialized_[current_context_id_])
00049           {
00050             //std::cout << "Initializing context no. " << current_context_id_ << std::endl;
00051             contexts_[current_context_id_].init();
00052             //create one queue per device:
00053             std::vector<viennacl::ocl::device> devices = contexts_[current_context_id_].devices();
00054             for (size_t j = 0; j<devices.size(); ++j)
00055               contexts_[current_context_id_].add_queue(devices[j]);
00056             initialized_[current_context_id_] = true;
00057             /*
00058             std::cout << "Context no. " << current_context_id_ << " initialized with " << devices.size() << " devices" << std::endl;
00059             std::cout << "Device id: " << devices[0].id() << std::endl;
00060             std::cout << "Current device id: " << contexts_[current_context_id_].current_device().id() << std::endl; */
00061           }
00062           return contexts_[current_context_id_];
00063         }
00064         
00066         static viennacl::ocl::command_queue & get_queue()
00067         {
00068           return current_context().get_queue();
00069         }
00070 
00076         static void setup_context(long i,
00077                                   std::vector<cl_device_id> const & devices)
00078         {
00079           if (initialized_[i])
00080             std::cerr << "ViennaCL: Warning in init_context(): Providing a list of devices has no effect, because context for ViennaCL is already created!" << std::endl;
00081           else
00082           {
00083             //set devices for context:
00084             for (size_t j = 0; j<devices.size(); ++j)
00085               contexts_[i].add_device(devices[j]);
00086           }
00087         }
00088 
00096         static void setup_context(long i,
00097                                   cl_context c,
00098                                   std::vector<cl_device_id> const & devices,
00099                                   std::map< cl_device_id, std::vector< cl_command_queue > > const & queues)
00100         {
00101           assert(devices.size() == queues.size() && "ViennaCL expects one queue per device!");
00102           
00103           if (initialized_[i])
00104             std::cerr << "ViennaCL: Warning in init_context(): Providing a list of devices has no effect, because context for ViennaCL is already created!" << std::endl;
00105           else
00106           {
00107             //set devices for context:
00108             for (size_t j = 0; j<devices.size(); ++j)
00109               contexts_[i].add_device(devices[j]);
00110             
00111             //init context:
00112             contexts_[i].init(c);
00113             
00114             //add queues:
00115             typedef typename std::map< cl_device_id, std::vector< cl_command_queue > >::const_iterator queue_iterator;
00116             for (queue_iterator qit = queues.begin();
00117                                 qit != queues.end();
00118                               ++qit)
00119             {
00120               std::vector<cl_command_queue> const & queues_for_device = qit->second;
00121               for (size_t j=0; j<queues_for_device.size(); ++j)
00122                 contexts_[i].add_queue(qit->first, queues_for_device[j]);
00123             }
00124             
00125             initialized_[i] = true;
00126           }
00127         }
00128 
00136         static void setup_context(long i, cl_context c, std::vector<cl_device_id> const & devices, std::vector<cl_command_queue> const & queue)
00137         {
00138           assert(devices.size() == queue.size() && "ViennaCL expects one queue per device!");
00139           
00140           //wrap queue vector into map
00141           std::map< cl_device_id, std::vector<cl_command_queue> > queues_map;
00142           for (size_t j = 0; j<devices.size(); ++j)
00143             queues_map[devices[j]].push_back(queue[j]);
00144           
00145           setup_context(i, c, devices, queues_map);
00146         }
00147 
00149         static void set_context_device_type(long i, cl_device_type t)
00150         {
00151           contexts_[i].default_device_type(t);
00152         }
00153 
00154       private:
00155         static long current_context_id_;
00156         static std::map<long, bool> initialized_;
00157         static std::map<long, viennacl::ocl::context> contexts_;
00158     };
00159     
00160     template <bool dummy>
00161     long backend<dummy>::current_context_id_ = 0;
00162 
00163     template <bool dummy>
00164     std::map<long, bool> backend<dummy>::initialized_;
00165 
00166     template <bool dummy>
00167     std::map<long, viennacl::ocl::context> backend<dummy>::contexts_;
00168     
00170 
00171     inline viennacl::ocl::context & current_context()
00172     {
00173       return viennacl::ocl::backend<>::current_context();
00174     }
00175 
00177     inline void switch_context(long i)
00178     {
00179       viennacl::ocl::backend<>::switch_context(i);
00180     }
00181     
00182 
00184     inline void setup_context(long i,
00185                               std::vector<cl_device_id> const & devices)
00186     {
00187       viennacl::ocl::backend<>::setup_context(i, devices);
00188     }
00189 
00191     inline void setup_context(long i,
00192                               cl_context c,
00193                               std::vector<cl_device_id> const & devices,
00194                               std::map< cl_device_id, std::vector<cl_command_queue> > const & queues)
00195     {
00196       viennacl::ocl::backend<>::setup_context(i, c, devices, queues);
00197     }
00198     
00200     inline void setup_context(long i, cl_context c, std::vector<cl_device_id> const & devices, std::vector<cl_command_queue> const & queues)
00201     {
00202       viennacl::ocl::backend<>::setup_context(i, c, devices, queues);
00203     }
00204 
00206     inline void setup_context(long i, cl_context c, cl_device_id d, cl_command_queue q)
00207     {
00208       std::vector<cl_device_id> devices(1);
00209       std::vector<cl_command_queue> queues(1);
00210       devices[0] = d;
00211       queues[0] = q;
00212       viennacl::ocl::backend<>::setup_context(i, c, devices, queues);
00213     }
00214 
00216     inline void set_context_device_type(long i, cl_device_type dev_type)
00217     {
00218       viennacl::ocl::backend<>::set_context_device_type(i, dev_type);
00219     }
00220 
00222     inline void set_context_device_type(long i, viennacl::ocl::gpu_tag)
00223     {
00224       set_context_device_type(i, CL_DEVICE_TYPE_GPU);
00225     }
00226 
00228     inline void set_context_device_type(long i, viennacl::ocl::cpu_tag)
00229     {
00230       set_context_device_type(i, CL_DEVICE_TYPE_CPU);
00231     }
00232 
00234     inline void set_context_device_type(long i, viennacl::ocl::default_tag)
00235     {
00236       set_context_device_type(i, CL_DEVICE_TYPE_DEFAULT);
00237     }
00238 
00240     inline void set_context_device_type(long i, viennacl::ocl::accelerator_tag)
00241     {
00242       set_context_device_type(i, CL_DEVICE_TYPE_ACCELERATOR);
00243     }
00244 
00246 
00247     inline viennacl::ocl::command_queue & get_queue()
00248     {
00249       return viennacl::ocl::current_context().get_queue();
00250     }
00251     
00253     inline viennacl::ocl::command_queue & get_queue(viennacl::ocl::device d, unsigned int queue_id = 0)
00254     {
00255       return viennacl::ocl::current_context().get_queue(d.id(), queue_id);
00256     }
00257 
00259     inline viennacl::ocl::command_queue & get_queue(cl_device_id dev_id, unsigned int queue_id = 0)
00260     {
00261       return viennacl::ocl::current_context().get_queue(dev_id, queue_id);
00262     }
00263 
00264 
00266     inline viennacl::ocl::kernel & get_kernel(std::string const & prog_name, std::string const & kernel_name)
00267     {
00268       return viennacl::ocl::current_context().get_program(prog_name).get_kernel(kernel_name);
00269     }
00270 
00272     inline void switch_device(viennacl::ocl::device & d)
00273     {
00274       viennacl::ocl::current_context().switch_device(d);
00275     }
00276     
00278     inline viennacl::ocl::device const & current_device()
00279     {
00280       return viennacl::ocl::current_context().current_device();
00281     }
00282 
00283   } //ocl
00284 } //viennacl
00285 #endif

Generated on Sat May 21 2011 20:36:50 for ViennaCL - The Vienna Computing Library by  doxygen 1.7.1