Extended CUDA Library (ecuda)  2.0
 All Classes Namespaces Files Functions Variables Typedefs Friends Macros
cube.hpp
Go to the documentation of this file.
1 /*
2 Copyright (c) 2014-2016, Scott Zuyderduyn
3 All rights reserved.
4 
5 Redistribution and use in source and binary forms, with or without
6 modification, are permitted provided that the following conditions are met:
7 
8 1. Redistributions of source code must retain the above copyright notice, this
9  list of conditions and the following disclaimer.
10 2. Redistributions in binary form must reproduce the above copyright notice,
11  this list of conditions and the following disclaimer in the documentation
12  and/or other materials provided with the distribution.
13 
14 THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
15 ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
16 WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
17 DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR
18 ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
19 (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
20 LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
21 ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
22 (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
23 SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
24 
25 The views and conclusions contained in the software and documentation are those
26 of the authors and should not be interpreted as representing official policies,
27 either expressed or implied, of the FreeBSD Project.
28 */
29 
30 //----------------------------------------------------------------------------
31 // cube.hpp
32 // An STL-like structure that resides in video memory.
33 //
34 // Author: Scott D. Zuyderduyn, Ph.D. (scott.zuyderduyn@utoronto.ca)
35 //----------------------------------------------------------------------------
36 
37 #pragma once
38 #ifndef ECUDA_CUBE_HPP
39 #define ECUDA_CUBE_HPP
40 
41 #include <limits>
42 #include <stdexcept>
43 #include <vector>
44 
45 #include "global.hpp"
46 #include "allocators.hpp"
47 #include "matrix.hpp"
48 #include "memory.hpp"
49 #include "type_traits.hpp"
50 
53 #include "model/device_matrix.hpp"
55 
56 namespace ecuda {
57 
59 namespace impl {
60 
61 template<typename T,class Alloc> class cube_kernel_argument; // forward declaration
62 
63 } // namespace impl
65 
128 template< typename T, class Alloc=device_pitch_allocator<T>, class P=shared_ptr<T> >
129 class cube : private model::device_contiguous_row_matrix< T, /*padded_ptr< T,*/ P /*>*/ > {
130 
131 private:
132  typedef model::device_contiguous_row_matrix< T, /*padded_ptr< T,*/ P /*>*/ > base_type;
133 
134 public:
135  typedef typename base_type::value_type value_type;
136  typedef Alloc allocator_type;
137  typedef typename base_type::size_type size_type;
138  typedef typename base_type::difference_type difference_type;
139  typedef typename base_type::reference reference;
140  typedef typename base_type::const_reference const_reference;
141  typedef typename base_type::pointer pointer;
142  typedef typename make_const<pointer>::type const_pointer;
143 
144  typedef model::device_sequence< value_type, striding_padded_ptr<value_type,typename ecuda::add_pointer<value_type>::type> > row_type;
145  typedef model::device_sequence< value_type, striding_padded_ptr<value_type,typename ecuda::add_pointer<value_type>::type> > column_type;
146  typedef model::device_contiguous_sequence<value_type > depth_type;
147  typedef model::device_sequence< const value_type, striding_padded_ptr<const value_type,typename ecuda::add_pointer<const value_type>::type> > const_row_type;
148  typedef model::device_sequence< const value_type, striding_padded_ptr<const value_type,typename ecuda::add_pointer<const value_type>::type> > const_column_type;
149  typedef model::device_contiguous_sequence<const value_type > const_depth_type;
150 
151  typedef typename base_type::iterator iterator;
152  typedef typename base_type::const_iterator const_iterator;
153  typedef typename base_type::reverse_iterator reverse_iterator;
154  typedef typename base_type::const_reverse_iterator const_reverse_iterator;
155 
156  typedef model::device_matrix< value_type, striding_padded_ptr<value_type,typename ecuda::add_pointer<value_type>::type> > slice_xy_type;
157  typedef model::device_contiguous_row_matrix< value_type, typename ecuda::add_pointer<value_type>::type > slice_xz_type;
158  typedef model::device_contiguous_row_matrix< value_type, typename ecuda::add_pointer<value_type>::type > slice_yz_type;
159  typedef model::device_matrix< const value_type, striding_padded_ptr<const value_type,typename ecuda::add_pointer<const value_type>::type> > const_slice_xy_type;
160  typedef model::device_contiguous_row_matrix< const value_type, typename ecuda::add_pointer<const value_type>::type > const_slice_xz_type;
161  typedef model::device_contiguous_row_matrix< const value_type, typename ecuda::add_pointer<const value_type>::type > const_slice_yz_type;
162 
163  typedef impl::cube_kernel_argument<T,Alloc> kernel_argument;
164  typedef const impl::cube_kernel_argument<T,Alloc> const_kernel_argument;
165 
166 private:
167  size_type numberRows;
168  allocator_type allocator;
169 
170  template<typename U,class Alloc2,class Q> friend class cube;
171 
172 protected:
176  template<typename U>
177  __HOST__ __DEVICE__ cube( const cube<T,Alloc,U>& src, ecuda::true_type ) : base_type( unmanaged_cast(src.get_pointer()), src.number_rows()*src.number_columns(), src.number_depths() ), numberRows(src.numberRows), allocator(src.allocator) {}
178 
182  __HOST__ __DEVICE__ cube& shallow_assign( const cube& other )
183  {
184  base_type::get_pointer() = other.get_pointer();
185  allocator = other.allocator;
186  numberRows = other.numberRows;
187  return *this;
188  }
189 
190 private:
191  __HOST__ void init()
192  {
193  if( number_rows() && number_columns() && number_depths() ) {
194  typename Alloc::pointer p = get_allocator().allocate( number_depths(), number_rows()*number_columns() );
195  typedef typename ecuda::add_pointer<value_type>::type raw_pointer_type;
196  shared_ptr<value_type> sp( naked_cast<raw_pointer_type>(p) );
197  padded_ptr< value_type, shared_ptr<value_type> > pp( sp, p.get_pitch() );
198  base_type base( pp, number_rows()*number_columns(), number_depths() );
199  base_type::swap( base );
200  }
201  }
202 
203 public:
214  const size_type numberRows=0, const size_type numberColumns=0, const size_type numberDepths=0,
215  const value_type& value = value_type(),
216  const Alloc& allocator = Alloc()
217  ) : base_type( pointer(), numberRows*numberColumns, numberDepths ), numberRows(numberRows), allocator(allocator)
218  {
219  init();
220  if( size() ) ecuda::fill( begin(), end(), value );
221  }
222 
230  __HOST__ cube( const cube& src ) :
231  base_type( pointer(), src.number_rows()*src.number_columns(), src.number_depths() ),
232  numberRows( src.numberRows ),
233  allocator( src.get_allocator() )
234  //allocator( std::allocator_traits<Alloc>::select_on_container_copy_construction(src.get_allocator()) )
235  {
236  init();
237  if( size() ) ecuda::copy( src.begin(), src.end(), begin() );
238  }
239 
248  __HOST__ cube( const cube& src, const allocator_type& alloc ) :
249  base_type( pointer(), src.number_rows()*src.number_columns(), src.number_depths() ),
250  numberRows( src.numberRows ),
251  allocator(alloc)
252  {
253  init();
254  if( size() ) ecuda::copy( src.begin(), src.end(), begin() );
255  }
256 
257  __HOST__ cube& operator=( const cube& src )
258  {
259  if( number_rows() != src.number_rows() || number_columns() != src.number_columns() || number_depths() != src.number_depths() ) {
260  resize( src.number_rows(), src.number_columns(), src.number_depths() );
261  }
262  if( size() ) ecuda::copy( src.begin(), src.end(), begin() );
263  return *this;
264  }
265 
266  #ifdef ECUDA_CPP11_AVAILABLE
267  __HOST__ cube( cube&& src ) : base_type(std::move(src)), numberRows(std::move(src.numberRows)), allocator(std::move(src.allocator)) {}
275 
276  __HOST__ cube& operator=( cube&& src ) {
277  base_type::operator=(std::move(src));
278  allocator = std::move(src.allocator);
279  numberRows = std::move(src.numberRows);
280  return *this;
281  }
282  #endif
283 
288  __HOST__ inline allocator_type get_allocator() const { return allocator; }
289 
295  __HOST__ __DEVICE__ inline size_type number_rows() const __NOEXCEPT__ { return numberRows; }
296 
302  __HOST__ __DEVICE__ inline size_type number_columns() const __NOEXCEPT__ { return base_type::number_rows()/numberRows; } //TODO: this costs a register in kernel code
303 
309  __HOST__ __DEVICE__ inline size_type number_depths() const __NOEXCEPT__ { return base_type::number_columns(); }
310 
318  __HOST__ __DEVICE__ inline size_type size() const __NOEXCEPT__ { return base_type::size(); }
319 
324  __HOST__ __DEVICE__ inline bool empty() const __NOEXCEPT__ { return !size(); }
325 
331  __HOST__ __DEVICE__ inline pointer data() __NOEXCEPT__ { return base_type::get_pointer(); }
332 
338  __HOST__ __DEVICE__ inline const_pointer data() const __NOEXCEPT__ { return base_type::get_pointer(); }
339 
347  __HOST__ __DEVICE__ inline iterator begin() __NOEXCEPT__ { return base_type::begin(); }
348 
356  __HOST__ __DEVICE__ inline iterator end() __NOEXCEPT__ { return base_type::end(); }
357 
365  __HOST__ __DEVICE__ inline const_iterator begin() const __NOEXCEPT__ { return base_type::begin(); }
366 
374  __HOST__ __DEVICE__ inline const_iterator end() const __NOEXCEPT__ { return base_type::end(); }
375 
383  __HOST__ __DEVICE__ inline reverse_iterator rbegin() __NOEXCEPT__ { return base_type::rbegin(); }
384 
393  __HOST__ __DEVICE__ inline reverse_iterator rend() __NOEXCEPT__ { return base_type::rend(); }
394 
402  __HOST__ __DEVICE__ inline const_reverse_iterator rbegin() const __NOEXCEPT__ { return base_type::rbegin(); }
403 
412  __HOST__ __DEVICE__ inline const_reverse_iterator rend() const __NOEXCEPT__ { return base_type::rend(); }
413 
414  #ifdef ECUDA_CPP11_AVAILABLE
415  __HOST__ __DEVICE__ inline const_iterator cbegin() const __NOEXCEPT__ { return base_type::cbegin(); }
416  __HOST__ __DEVICE__ inline const_iterator cend() const __NOEXCEPT__ { return base_type::cend(); }
417  __HOST__ __DEVICE__ inline const_reverse_iterator crbegin() __NOEXCEPT__ { return base_type::crbegin(); }
418  __HOST__ __DEVICE__ inline const_reverse_iterator crend() __NOEXCEPT__ { return base_type::crend(); }
419  #endif
420 
428  __HOST__ __DEVICE__ row_type get_row( const size_type columnIndex, const size_type depthIndex )
429  {
430  typedef typename make_unmanaged<typename base_type::pointer>::type unmanaged_pointer_type;
431  unmanaged_pointer_type ptr = unmanaged_cast( base_type::get_pointer() ); // padded_ptr
432  ptr.skip_bytes( columnIndex*ptr.get_pitch() ); // move pointer to correct column
433  ptr += depthIndex; // move pointer to correct depth
434  typename row_type::pointer ptr2( ptr.get(), number_columns()*ptr.get_pitch() );
435  return row_type( ptr2, number_rows() );
436  }
437 
445  __HOST__ __DEVICE__ column_type get_column( const size_type rowIndex, const size_type depthIndex )
446  {
447  typedef typename make_unmanaged<typename base_type::pointer>::type unmanaged_pointer_type;
448  unmanaged_pointer_type ptr = unmanaged_cast( base_type::get_pointer() ); // padded_ptr
449  ptr.skip_bytes( rowIndex*number_columns()*ptr.get_pitch() ); // move pointer to correct column
450  ptr += depthIndex; // move pointer to correct depth
451  typename column_type::pointer ptr2( ptr.get(), ptr.get_pitch() );
452  return column_type( ptr2, number_columns() );
453  }
454 
462  __HOST__ __DEVICE__ depth_type get_depth( const size_type rowIndex, const size_type columnIndex )
463  {
464  typedef typename make_unmanaged<typename base_type::pointer>::type unmanaged_pointer_type;
465  unmanaged_pointer_type ptr = unmanaged_cast( base_type::get_pointer() );
466  ptr += rowIndex*number_columns()*number_depths()+columnIndex*number_depths(); // move pointer to depth start
467  return depth_type( naked_cast<typename ecuda::add_pointer<value_type>::type>(ptr), number_depths() );
468  }
469 
477  __HOST__ __DEVICE__ const_row_type get_row( const size_type columnIndex, const size_type depthIndex ) const
478  {
479  typedef typename make_unmanaged_const<typename base_type::pointer>::type unmanaged_pointer_type;
480  unmanaged_pointer_type ptr = unmanaged_cast( base_type::get_pointer() ); // padded_ptr
481  ptr.skip_bytes( columnIndex*ptr.get_pitch() ); // move pointer to correct column
482  ptr += depthIndex; // move pointer to correct depth
483  typename const_row_type::pointer ptr2( ptr.get(), number_columns()*ptr.get_pitch() );
484  return const_row_type( ptr2, number_rows() );
485  }
486 
494  __HOST__ __DEVICE__ const_column_type get_column( const size_type rowIndex, const size_type depthIndex ) const
495  {
496  typedef typename make_unmanaged_const<typename base_type::pointer>::type unmanaged_pointer_type;
497  unmanaged_pointer_type ptr = unmanaged_cast( base_type::get_pointer() ); // padded_ptr
498  ptr.skip_bytes( rowIndex*number_columns()*ptr.get_pitch() ); // move pointer to correct column
499  ptr += depthIndex; // move pointer to correct depth
500  typename const_column_type::pointer ptr2( ptr.get(), ptr.get_pitch() );
501  return const_column_type( ptr2, number_columns() );
502  }
503 
511  __HOST__ __DEVICE__ const_depth_type get_depth( const size_type rowIndex, const size_type columnIndex ) const
512  {
513  typedef typename make_unmanaged_const<typename base_type::pointer>::type unmanaged_pointer_type;
514  unmanaged_pointer_type ptr = unmanaged_cast( base_type::get_pointer() );
515  ptr += rowIndex*number_columns()*number_depths()+columnIndex*number_depths(); // move pointer to depth start
516  return const_depth_type( naked_cast<typename ecuda::add_pointer<const value_type>::type>(ptr), number_depths() );
517  }
518 
526  {
527  typedef typename make_unmanaged<typename base_type::pointer>::type unmanaged_pointer_type;
528  unmanaged_pointer_type ptr = unmanaged_cast( base_type::get_pointer() );
529  ptr += rowIndex*number_columns()*number_depths();
530  return slice_yz_type( ptr, number_columns(), number_depths() );
531  }
532 
540  {
541  typedef typename make_unmanaged<typename base_type::pointer>::type unmanaged_pointer_type;
542  unmanaged_pointer_type ptr = unmanaged_cast( base_type::get_pointer() ); // padded_ptr
543  ptr += depthIndex; // move to correct depth
544  typename slice_xy_type::pointer ptr2( ptr.get(), ptr.get_pitch() ); // make pointer stride over depths
545  return slice_xy_type( ptr2, number_rows(), number_columns() );
546  }
547 
555  {
556  typedef typename make_unmanaged<typename base_type::pointer>::type unmanaged_pointer_type;
557  unmanaged_pointer_type ptr = unmanaged_cast( base_type::get_pointer() ); // padded_ptr
558  typename slice_xz_type::pointer ptr2( ptr.get(), ptr.get_pitch()*number_columns() ); // extend pitch
559  ptr2 += columnIndex*number_depths(); // move to correct column
560  return slice_xz_type( ptr2, number_rows(), number_depths() );
561  }
562 
570  {
571  typedef typename make_unmanaged_const<typename base_type::pointer>::type unmanaged_pointer_type;
572  unmanaged_pointer_type ptr = unmanaged_cast( base_type::get_pointer() );
573  ptr += rowIndex*number_columns()*number_depths();
575  }
576 
584  {
585  typedef typename make_unmanaged_const<typename base_type::pointer>::type unmanaged_pointer_type;
586  unmanaged_pointer_type ptr = unmanaged_cast( base_type::get_pointer() ); // padded_ptr
587  ptr += depthIndex; // move to correct depth
588  typename const_slice_xy_type::pointer ptr2( ptr.get(), ptr.get_pitch() ); // make pointer stride over depths
589  return const_slice_xy_type( ptr2, number_rows(), number_columns() );
590  }
591 
599  {
600  typedef typename make_unmanaged_const<typename base_type::pointer>::type unmanaged_pointer_type;
601  unmanaged_pointer_type ptr = unmanaged_cast( base_type::get_pointer() ); // padded_ptr
602  typename const_slice_xz_type::pointer ptr2( ptr.get(), ptr.get_pitch()*number_columns() ); // extend pitch
603  ptr2 += columnIndex*number_depths(); // move to correct column
604  return const_slice_xz_type( ptr2, number_rows(), number_depths() );
605  }
606 
618  __DEVICE__ inline reference at( size_type rowIndex, size_type columnIndex, size_type depthIndex )
619  {
620  if( rowIndex >= number_rows() || columnIndex >= number_columns() || depthIndex >= number_depths() ) {
621  #ifndef __CUDACC__
622  throw std::out_of_range( EXCEPTION_MSG("ecuda::cube::at() row, column and/or depth index parameter is out of range") );
623  #else
624  // this strategy is taken from:
625  // http://stackoverflow.com/questions/12521721/crashing-a-kernel-gracefully
627  //__threadfence();
628  asm("trap;");
629  #endif
630  }
631  return base_type::at( rowIndex*number_columns()+columnIndex, depthIndex );
632  }
633 
645  __DEVICE__ inline const_reference at( size_type rowIndex, size_type columnIndex, size_type depthIndex ) const
646  {
647  if( rowIndex >= number_rows() || columnIndex >= number_columns() || depthIndex >= number_depths() ) {
648  #ifndef __CUDACC__
649  throw std::out_of_range( EXCEPTION_MSG("ecuda::cube::at() row, column and/or depth index parameter is out of range") );
650  #else
651  // this strategy is taken from:
652  // http://stackoverflow.com/questions/12521721/crashing-a-kernel-gracefully
654  //__threadfence();
655  asm("trap;");
656  #endif
657  }
658  return base_type::at( rowIndex*number_columns()+columnIndex, depthIndex );
659  }
660 
671  __DEVICE__ inline reference operator()( const size_type rowIndex, const size_type columnIndex, const size_type depthIndex ) { return base_type::at( rowIndex*number_columns()+columnIndex, depthIndex ); }
672 
683  __DEVICE__ inline const_reference operator()( const size_type rowIndex, const size_type columnIndex, const size_type depthIndex ) const { return base_type::at( rowIndex*number_columns()+columnIndex, depthIndex ); }
684 
690  __HOST__ __DEVICE__ inline slice_yz_type operator[]( const size_type rowIndex ) { return get_yz( rowIndex ); }
691 
697  __HOST__ __DEVICE__ inline const_slice_yz_type operator[]( const size_type rowIndex ) const { return get_yz( rowIndex ); }
698 
709  __HOST__ void resize( const size_type newNumberRows, const size_type newNumberColumns, const size_type newNumberDepths, const value_type& value = value_type() )
710  {
711  if( number_rows() == newNumberRows && number_columns() == newNumberColumns && number_depths() == newNumberDepths ) return; // no resize needed
712  cube newCube( newNumberRows, newNumberColumns, newNumberDepths, value, get_allocator() );
713  for( size_type i = 0; i < std::min(newNumberRows,number_rows()); ++i ) {
714  for( size_type j = 0; j < std::min(newNumberColumns,number_columns()); ++j ) {
715  depth_type inputDepth = get_depth(i,j);
716  depth_type outputDepth = newCube.get_depth(i,j);
717  ecuda::copy( inputDepth.begin(), inputDepth.begin()+std::min(newNumberDepths,number_depths()), outputDepth.begin() );
718  }
719  }
720  base_type::swap( newCube );
721  numberRows = newNumberRows;
722  }
723 
729  __HOST__ __DEVICE__ inline void fill( const value_type& value ) { if( !empty() ) ecuda::fill( begin(), end(), value ); }
730 
731 };
732 
734 namespace impl {
735 
745 template< typename T, class Alloc=device_pitch_allocator<T> >
746 class cube_kernel_argument : public cube<T,Alloc,typename ecuda::add_pointer<T>::type>
747 {
748 
749 private:
750  typedef cube<T,Alloc,typename ecuda::add_pointer<T>::type> base_type;
751 
752 public:
753  template<class P>
754  __HOST__ cube_kernel_argument( const cube<T,Alloc,P>& src ) : base_type( src, ecuda::true_type() ) {}
755 
756  __HOST__ __DEVICE__ cube_kernel_argument( const cube_kernel_argument& src ) : base_type( src, ecuda::true_type() ) {}
757 
758  template<class P>
759  __HOST__ cube_kernel_argument& operator=( const cube<T,Alloc,P>& src )
760  {
761  base_type::shallow_assign( src );
762  return *this;
763  }
764 
765  #ifdef ECUDA_CPP11_AVAILABLE
766  cube_kernel_argument( cube_kernel_argument&& src ) : base_type(std::move(src)) {}
767 
768  cube_kernel_argument& operator=( cube_kernel_argument&& src )
769  {
770  base_type::operator=(std::move(src));
771  return *this;
772  }
773  #endif
774 
775 };
776 
777 } // namespace impl
779 
780 } // namespace ecuda
781 
782 #endif
783 
base_type::iterator iterator
iterator type
Definition: cube.hpp:151
base_type::value_type value_type
cell data type
Definition: cube.hpp:135
__HOST__ __DEVICE__ reverse_iterator rend() __NOEXCEPT__
Returns a reverse iterator to the element following the last element of the reversed container...
Definition: cube.hpp:393
__HOST__ allocator_type get_allocator() const
Returns the allocator associated with the container.
Definition: cube.hpp:288
__HOST__ cube(const cube &src, const allocator_type &alloc)
Copy constructor.
Definition: cube.hpp:248
__HOST__ __DEVICE__ OutputIterator copy(InputIterator first, InputIterator last, OutputIterator result)
Replacement for std::copy.
Definition: copy.hpp:801
base_type::pointer pointer
cell pointer type
Definition: cube.hpp:141
__HOST__ __DEVICE__ const_slice_yz_type get_yz(const size_type rowIndex) const
Gets a view of the matrix of elements at a single row.
Definition: cube.hpp:569
__HOST__ __DEVICE__ const_reverse_iterator rend() const __NOEXCEPT__
Returns a reverse iterator to the element following the last element of the reversed container...
Definition: cube.hpp:412
__HOST__ __DEVICE__ const_pointer data() const __NOEXCEPT__
Returns pointer to the underlying 2D memory serving as element storage.
Definition: cube.hpp:338
__DEVICE__ reference operator()(const size_type rowIndex, const size_type columnIndex, const size_type depthIndex)
Returns a reference to the element at specified location index. No bounds checking is performed...
Definition: cube.hpp:671
const impl::cube_kernel_argument< T, Alloc > const_kernel_argument
const kernel argument type
Definition: cube.hpp:164
__HOST__ __DEVICE__ slice_yz_type operator[](const size_type rowIndex)
operator[](rowIndex) alias for get_yz(rowIndex)
Definition: cube.hpp:690
__HOST__ __DEVICE__ reverse_iterator rbegin() __NOEXCEPT__
Returns a reverse iterator to the first element of the reversed container.
Definition: cube.hpp:383
__HOST__ void resize(const size_type newNumberRows, const size_type newNumberColumns, const size_type newNumberDepths, const value_type &value=value_type())
Resizes the container to have dimensions newNumberRows x newNumberColumns x newNumberDepths.
Definition: cube.hpp:709
__HOST__ __DEVICE__ slice_xy_type get_xy(const size_type depthIndex)
Gets a view of the matrix of elements at a single depth.
Definition: cube.hpp:539
__HOST__ cube(const size_type numberRows=0, const size_type numberColumns=0, const size_type numberDepths=0, const value_type &value=value_type(), const Alloc &allocator=Alloc())
Constructs a cube with dimensions numberRows x numberColumns x numberDepths filled with copies of ele...
Definition: cube.hpp:213
model::device_matrix< value_type, striding_padded_ptr< value_type, typename ecuda::add_pointer< value_type >::type > > slice_xy_type
xy section of a cube at a fixed depth
Definition: cube.hpp:156
__HOST__ __DEVICE__ const_row_type get_row(const size_type columnIndex, const size_type depthIndex) const
Gets a view of the sequence of elements forming a single row.
Definition: cube.hpp:477
model::device_matrix< const value_type, striding_padded_ptr< const value_type, typename ecuda::add_pointer< const value_type >::type > > const_slice_xy_type
xy section of a cube at a fixed depth
Definition: cube.hpp:159
__HOST__ __DEVICE__ slice_xz_type get_xz(const size_type columnIndex)
Gets a view of the matrix of elements at a single column.
Definition: cube.hpp:554
__HOST__ __DEVICE__ const_depth_type get_depth(const size_type rowIndex, const size_type columnIndex) const
Gets a view of the sequence of elements forming a single depth.
Definition: cube.hpp:511
base_type::reference reference
cell reference type
Definition: cube.hpp:139
__DEVICE__ const_reference at(size_type rowIndex, size_type columnIndex, size_type depthIndex) const
Returns a constant reference to the element at specified row, column, and depth index, with bounds checking.
Definition: cube.hpp:645
model::device_contiguous_row_matrix< value_type, typename ecuda::add_pointer< value_type >::type > slice_xz_type
xz section of a cube at a fixed column
Definition: cube.hpp:157
__HOST__ __DEVICE__ const_slice_xy_type get_xy(const size_type depthIndex) const
Gets a view of the matrix of elements at a single depth.
Definition: cube.hpp:583
Alloc allocator_type
allocator type
Definition: cube.hpp:136
#define __NOEXCEPT__
Definition: global.hpp:140
__HOST__ __DEVICE__ pointer data() __NOEXCEPT__
Returns pointer to the underlying 2D memory serving as element storage.
Definition: cube.hpp:331
base_type::const_reverse_iterator const_reverse_iterator
const reverse iterator type
Definition: cube.hpp:154
__HOST__ __DEVICE__ slice_yz_type get_yz(const size_type rowIndex)
Gets a view of the matrix of elements at a single row.
Definition: cube.hpp:525
__HOST__ __DEVICE__ size_type number_columns() const __NOEXCEPT__
Returns the number of columns in the container.
Definition: cube.hpp:302
model::device_contiguous_sequence< const value_type > const_depth_type
cube const depth container type
Definition: cube.hpp:149
__HOST__ __DEVICE__ const_iterator begin() const __NOEXCEPT__
Returns an iterator to the first element of the container.
Definition: cube.hpp:365
#define __HOST__
Definition: global.hpp:150
__HOST__ __DEVICE__ iterator end() __NOEXCEPT__
Returns an iterator to the element following the last element of the container.
Definition: cube.hpp:356
__HOST__ __DEVICE__ void swap(T &a, T &b) __NOEXCEPT__
Definition: algorithm.hpp:54
A resizable cube stored in device memory.
Definition: cube.hpp:129
base_type::const_iterator const_iterator
const iterator type
Definition: cube.hpp:152
make_const< pointer >::type const_pointer
cell const pointer type
Definition: cube.hpp:142
model::device_contiguous_row_matrix< const value_type, typename ecuda::add_pointer< const value_type >::type > const_slice_xz_type
const xz section of a cube at a fixed row
Definition: cube.hpp:160
__HOST__ __DEVICE__ size_type number_depths() const __NOEXCEPT__
Returns the number of depths in the container.
Definition: cube.hpp:309
__HOST__ __DEVICE__ const_iterator end() const __NOEXCEPT__
Returns an iterator to the element following the last element of the container.
Definition: cube.hpp:374
__DEVICE__ reference at(size_type rowIndex, size_type columnIndex, size_type depthIndex)
Returns a reference to the element at specified row, column, and depth index, with bounds checking...
Definition: cube.hpp:618
__HOST__ __DEVICE__ const_reverse_iterator rbegin() const __NOEXCEPT__
Returns a reverse iterator to the first element of the reversed container.
Definition: cube.hpp:402
model::device_sequence< value_type, striding_padded_ptr< value_type, typename ecuda::add_pointer< value_type >::type > > row_type
cube row container type
Definition: cube.hpp:144
__HOST__ cube(const cube &src)
Copy constructor.
Definition: cube.hpp:230
__HOST__ __DEVICE__ const_slice_yz_type operator[](const size_type rowIndex) const
operator[](rowIndex) alias for get_yz(rowIndex)
Definition: cube.hpp:697
__HOST__ __DEVICE__ void fill(const value_type &value)
Assigns a given value to all elements in the container.
Definition: cube.hpp:729
__HOST__ __DEVICE__ depth_type get_depth(const size_type rowIndex, const size_type columnIndex)
Gets a view of the sequence of elements forming a single depth.
Definition: cube.hpp:462
__HOST__ __DEVICE__ size_type number_rows() const __NOEXCEPT__
Returns the number of rows in the container.
Definition: cube.hpp:295
base_type::const_reference const_reference
cell const reference type
Definition: cube.hpp:140
__HOST__ __DEVICE__ size_type size() const __NOEXCEPT__
Returns the number of elements in the container.
Definition: cube.hpp:318
model::device_sequence< value_type, striding_padded_ptr< value_type, typename ecuda::add_pointer< value_type >::type > > column_type
cube column container type
Definition: cube.hpp:145
__HOST__ __DEVICE__ const T & min(const T &a, const T &b)
Definition: algorithm.hpp:48
__DEVICE__ const_reference operator()(const size_type rowIndex, const size_type columnIndex, const size_type depthIndex) const
Returns a reference to the element at specified location index. No bounds checking is performed...
Definition: cube.hpp:683
__HOST__ __DEVICE__ row_type get_row(const size_type columnIndex, const size_type depthIndex)
Gets a view of the sequence of elements forming a single row.
Definition: cube.hpp:428
__HOST__ __DEVICE__ const_slice_xz_type get_xz(const size_type columnIndex) const
Gets a view of the matrix of elements at a single column.
Definition: cube.hpp:598
__HOST__ __DEVICE__ column_type get_column(const size_type rowIndex, const size_type depthIndex)
Gets a view of the sequence of elements forming a single column.
Definition: cube.hpp:445
model::device_contiguous_row_matrix< const value_type, typename ecuda::add_pointer< const value_type >::type > const_slice_yz_type
const yz section of a cube at a fixed row
Definition: cube.hpp:161
base_type::size_type size_type
unsigned integral type
Definition: cube.hpp:137
__HOST__ __DEVICE__ bool empty() const __NOEXCEPT__
Checks if the container has no elements.
Definition: cube.hpp:324
base_type::reverse_iterator reverse_iterator
reverse iterator type
Definition: cube.hpp:153
model::device_contiguous_sequence< value_type > depth_type
cube depth container type
Definition: cube.hpp:146
model::device_sequence< const value_type, striding_padded_ptr< const value_type, typename ecuda::add_pointer< const value_type >::type > > const_column_type
cube const column container type
Definition: cube.hpp:148
__DEVICE__ void threadfence()
model::device_contiguous_row_matrix< value_type, typename ecuda::add_pointer< value_type >::type > slice_yz_type
yz section of a cube at a fixed row
Definition: cube.hpp:158
#define EXCEPTION_MSG(x)
Definition: global.hpp:92
#define __DEVICE__
Definition: global.hpp:151
__HOST__ cube & operator=(const cube &src)
Definition: cube.hpp:257
impl::cube_kernel_argument< T, Alloc > kernel_argument
kernel argument type
Definition: cube.hpp:163
friend class cube
Definition: cube.hpp:170
__HOST__ __DEVICE__ iterator begin() __NOEXCEPT__
Returns an iterator to the first element of the container.
Definition: cube.hpp:347
model::device_sequence< const value_type, striding_padded_ptr< const value_type, typename ecuda::add_pointer< const value_type >::type > > const_row_type
cube const row container type
Definition: cube.hpp:147
__HOST__ __DEVICE__ const_column_type get_column(const size_type rowIndex, const size_type depthIndex) const
Gets a view of the sequence of elements forming a single column.
Definition: cube.hpp:494
base_type::difference_type difference_type
signed integral type
Definition: cube.hpp:138
__HOST__ __DEVICE__ void fill(ForwardIterator first, ForwardIterator last, const T &val)
Definition: fill.hpp:156