YAKL
YAKL_FArray.h
Go to the documentation of this file.
1 
2 #pragma once
3 // Included by YAKL_Array.h
4 
6 namespace yakl {
7 
54  template <class T, int rank, int myMem>
55  class Array<T,rank,myMem,styleFortran> : public ArrayBase<T,rank,myMem,styleFortran> {
56  public:
57 
59  typedef typename std::remove_cv<T>::type type;
61  typedef T value_type;
64  typedef typename std::add_const<type>::type const_value_type;
67  typedef typename std::remove_const<type>::type non_const_value_type;
68 
69  //* @private */
70  int lbounds[rank]; // Lower bounds
71 
72 
73  // Start off all constructors making sure the pointers are null
75  YAKL_INLINE void nullify() {
76  this->myData = nullptr;
77  this->refCount = nullptr;
78  for (int i=0; i < rank; i++) { this->lbounds[i] = 1; this->dimension[i] = 0; }
79  #ifdef YAKL_DEBUG
80  this->myname="Uninitialized";
81  #endif
82  }
83 
84  /* CONSTRUCTORS
85  Always nullify before beginning so that myData == nullptr upon init.
86  */
89  nullify();
90  }
92  YAKL_INLINE explicit Array(char const * label) {
93  nullify();
94  #ifdef YAKL_DEBUG
95  this->myname = label;
96  #endif
97  }
98 
99 
124  YAKL_INLINE Array( char const* label , Bnd b1 ) : Array(label,Bnds(b1)) {
125  static_assert( rank == 1 , "ERROR: Calling constructor with 1 bound on non-rank-1 array" );
126  }
129  YAKL_INLINE Array( char const* label , Bnd b1 ,
130  Bnd b2 ) : Array(label,Bnds(b1,b2)) {
131  static_assert( rank == 2 , "ERROR: Calling constructor with 2 bound on non-rank-2 array" );
132  }
135  YAKL_INLINE Array( char const* label , Bnd b1 ,
136  Bnd b2 ,
137  Bnd b3 ) : Array(label,Bnds(b1,b2,b3)) {
138  static_assert( rank == 3 , "ERROR: Calling constructor with 3 bound on non-rank-3 array" );
139  }
142  YAKL_INLINE Array( char const* label , Bnd b1 ,
143  Bnd b2 ,
144  Bnd b3 ,
145  Bnd b4 ) : Array(label,Bnds(b1,b2,b3,b4)) {
146  static_assert( rank == 4 , "ERROR: Calling constructor with 4 bound on non-rank-4 array" );
147  }
150  YAKL_INLINE Array( char const* label , Bnd b1 ,
151  Bnd b2 ,
152  Bnd b3 ,
153  Bnd b4 ,
154  Bnd b5 ) : Array(label,Bnds(b1,b2,b3,b4,b5)) {
155  static_assert( rank == 5 , "ERROR: Calling constructor with 5 bound on non-rank-5 array" );
156  }
159  YAKL_INLINE Array( char const* label , Bnd b1 ,
160  Bnd b2 ,
161  Bnd b3 ,
162  Bnd b4 ,
163  Bnd b5 ,
164  Bnd b6 ) : Array(label,Bnds(b1,b2,b3,b4,b5,b6)) {
165  static_assert( rank == 6 , "ERROR: Calling constructor with 6 bound on non-rank-6 array" );
166  }
169  YAKL_INLINE Array( char const* label , Bnd b1 ,
170  Bnd b2 ,
171  Bnd b3 ,
172  Bnd b4 ,
173  Bnd b5 ,
174  Bnd b6 ,
175  Bnd b7 ) : Array(label,Bnds(b1,b2,b3,b4,b5,b6,b7)) {
176  static_assert( rank == 7 , "ERROR: Calling constructor with 7 bound on non-rank-7 array" );
177  }
180  YAKL_INLINE Array( char const* label , Bnd b1 ,
181  Bnd b2 ,
182  Bnd b3 ,
183  Bnd b4 ,
184  Bnd b5 ,
185  Bnd b6 ,
186  Bnd b7 ,
187  Bnd b8 ) : Array(label,Bnds(b1,b2,b3,b4,b5,b6,b7,b8)) {
188  static_assert( rank == 8 , "ERROR: Calling constructor with 8 bound on non-rank-8 array" );
189  }
192  YAKL_INLINE Array(char const * label, Bnds bnds) {
193  static_assert( rank >= 1 && rank <= 8 , "ERROR: Creating Array with a rank < 1 or > 8" );
194  nullify();
195  #ifdef YAKL_DEBUG
196  if ( bnds.size() < rank ) { yakl_throw("ERROR: Number of array bounds specified is < rank"); }
197  #endif
198  YAKL_EXECUTE_ON_HOST_ONLY( this->deallocate(); )
199  #ifdef YAKL_DEBUG
200  this->myname = label;
201  #endif
202  for (int i=0; i < rank; i++) { this->lbounds[i] = bnds[i].l; this->dimension[i] = bnds[i].u - bnds[i].l + 1; }
203  YAKL_EXECUTE_ON_HOST_ONLY( this->allocate(); )
204  }
205 
206 
234  YAKL_INLINE Array( char const *label , T *data, Bnd b1 ) : Array(label,data,Bnds(b1)) {
235  static_assert( rank == 1 , "ERROR: Calling constructor with 1 bound on non-rank-1 array" );
236  }
239  YAKL_INLINE Array( char const *label , T *data, Bnd b1 ,
240  Bnd b2 ) : Array(label,data,Bnds(b1,b2)) {
241  static_assert( rank == 2 , "ERROR: Calling constructor with 2 bound on non-rank-2 array" );
242  }
245  YAKL_INLINE Array( char const *label , T *data, Bnd b1 ,
246  Bnd b2 ,
247  Bnd b3 ) : Array(label,data,Bnds(b1,b2,b3)) {
248  static_assert( rank == 3 , "ERROR: Calling constructor with 3 bound on non-rank-3 array" );
249  }
252  YAKL_INLINE Array( char const *label , T *data, Bnd b1 ,
253  Bnd b2 ,
254  Bnd b3 ,
255  Bnd b4 ) : Array(label,data,Bnds(b1,b2,b3,b4)) {
256  static_assert( rank == 4 , "ERROR: Calling constructor with 4 bound on non-rank-4 array" );
257  }
260  YAKL_INLINE Array( char const *label , T *data, Bnd b1 ,
261  Bnd b2 ,
262  Bnd b3 ,
263  Bnd b4 ,
264  Bnd b5 ) : Array(label,data,Bnds(b1,b2,b3,b4,b5)) {
265  static_assert( rank == 5 , "ERROR: Calling constructor with 5 bound on non-rank-5 array" );
266  }
269  YAKL_INLINE Array( char const *label , T *data, Bnd b1 ,
270  Bnd b2 ,
271  Bnd b3 ,
272  Bnd b4 ,
273  Bnd b5 ,
274  Bnd b6 ) : Array(label,data,Bnds(b1,b2,b3,b4,b5,b6)) {
275  static_assert( rank == 6 , "ERROR: Calling constructor with 6 bound on non-rank-6 array" );
276  }
279  YAKL_INLINE Array( char const *label , T *data, Bnd b1 ,
280  Bnd b2 ,
281  Bnd b3 ,
282  Bnd b4 ,
283  Bnd b5 ,
284  Bnd b6 ,
285  Bnd b7 ) : Array(label,data,Bnds(b1,b2,b3,b4,b5,b6,b7)) {
286  static_assert( rank == 7 , "ERROR: Calling constructor with 7 bound on non-rank-7 array" );
287  }
290  YAKL_INLINE Array( char const *label , T *data, Bnd b1 ,
291  Bnd b2 ,
292  Bnd b3 ,
293  Bnd b4 ,
294  Bnd b5 ,
295  Bnd b6 ,
296  Bnd b7 ,
297  Bnd b8 ) : Array(label,data,Bnds(b1,b2,b3,b4,b5,b6,b7,b8)) {
298  static_assert( rank == 8 , "ERROR: Calling constructor with 8 bound on non-rank-8 array" );
299  }
302  YAKL_INLINE Array(char const *label, T *data, Bnds bnds) {
303  static_assert( rank >= 1 && rank <= 8 , "ERROR: Creating Array with a rank < 1 or > 8" );
304  nullify();
305  #ifdef YAKL_DEBUG
306  if ( bnds.size() < rank ) { yakl_throw("ERROR: Number of array bounds specified is < rank"); }
307  if (data == nullptr) yakl_throw("ERROR: wrapping nullptr with a YAKL Array object");
308  this->myname = label;
309  #endif
310  for (int i=0; i < rank; i++) { this->lbounds[i] = bnds[i].l; this->dimension[i] = bnds[i].u - bnds[i].l + 1; }
311  this->myData = data;
312  this->refCount = nullptr;
313  }
314 
315 
316  /*
317  COPY CONSTRUCTORS / FUNCTIONS
318  This shares the pointers with another Array and increments the refCounter
319  */
322  // This is a constructor, so no need to deallocate
323  nullify();
324  copy_constructor_common(rhs);
325  }
328  static_assert( std::is_const<T>::value ,
329  "ERROR: Cannot create non-const Array using const Array" );
330  // This is a constructor, so no need to deallocate
331  nullify();
332  copy_constructor_common(rhs);
333  }
334 
335 
338  if constexpr (! std::is_const<T>::value) {
339  if (this == &rhs) { return *this; }
340  }
341  YAKL_EXECUTE_ON_HOST_ONLY( this->deallocate(); )
342  copy_constructor_common(rhs);
343  return *this;
344  }
347  static_assert( std::is_const<T>::value ,
348  "ERROR: Cannot create non-const Array using const Array" );
349  if constexpr (std::is_const<T>::value) {
350  if (this == &rhs) { return *this; }
351  }
352  YAKL_EXECUTE_ON_HOST_ONLY( this->deallocate(); )
353  copy_constructor_common(rhs);
354  return *this;
355  }
356 
358  template <class TLOC>
359  YAKL_INLINE void copy_constructor_common(Array<TLOC,rank,myMem,styleFortran> const &rhs) {
360  for (int i=0; i<rank; i++) {
361  this->lbounds[i] = rhs.lbounds[i]; this->dimension[i] = rhs.dimension[i];
362  }
363  #ifdef YAKL_DEBUG
364  this->myname = rhs.myname;
365  #endif
366  this->myData = rhs.myData;
367  YAKL_EXECUTE_ON_HOST_ONLY( yakl_mtx_lock(); )
368  this->refCount = rhs.refCount;
369  if (this->refCount != nullptr) {
370  // YAKL_EXECUTE_ON_HOST_ONLY( (*(this->refCount))++; ) // This gives an nvc++ error
371  YAKL_EXECUTE_ON_HOST_ONLY( { (*(this->refCount))++; } ) // This works around the nvc++ error
372  }
373  YAKL_EXECUTE_ON_HOST_ONLY( yakl_mtx_unlock(); )
374  }
375 
376 
377  /*
378  MOVE CONSTRUCTORS
379  This steals the pointers form the rhs instead of sharing and sets rhs pointers to nullptr.
380  Therefore, no need to increment reference counter
381  */
384  // This is a constructor, so no need to deallocate
385  nullify();
386  for (int i=0; i<rank; i++) {
387  this->lbounds[i] = rhs.lbounds[i]; this->dimension[i] = rhs.dimension[i];
388  }
389  #ifdef YAKL_DEBUG
390  this->myname = rhs.myname;
391  #endif
392  this->myData = rhs.myData;
393  rhs.myData = nullptr;
394 
395  this->refCount = rhs.refCount;
396  rhs.refCount = nullptr;
397  }
398 
399 
402  if (this == &rhs) { return *this; }
403  YAKL_EXECUTE_ON_HOST_ONLY( this->deallocate(); )
404  for (int i=0; i<rank; i++) {
405  this->lbounds [i] = rhs.lbounds [i]; this->dimension[i] = rhs.dimension[i];
406  }
407  #ifdef YAKL_DEBUG
408  this->myname = rhs.myname;
409  #endif
410  this->myData = rhs.myData;
411  rhs.myData = nullptr;
412 
413  this->refCount = rhs.refCount;
414  rhs.refCount = nullptr;
415 
416  return *this;
417  }
418 
419 
420  /*
421  DESTRUCTOR
422  Decrement the refCounter, and if it's zero, deallocate and nullify.
423  */
426  YAKL_EXECUTE_ON_HOST_ONLY( this->deallocate(); )
427  }
428 
429 
434  Array( array_ir::ArrayIR<T,rank> const &ir , std::vector<int> lower_bounds = std::vector<int>() ) {
435  nullify();
436  if (myMem == memDevice && (! ir.data_valid_on_device())) yakl_throw("ERROR: wrapping non-device-valid ArrayIR with memDevice yakl::FArray");
437  if (myMem == memHost && (! ir.data_valid_on_host ())) yakl_throw("ERROR: wrapping non-host-valid ArrayIR with memHost yakl::FArray");
438  this->myData = ir.data();
439  #ifdef YAKL_DEBUG
440  this->myname = ir.label();
441  #endif
442  for (int i=0; i < rank; i++) { this->dimension[i] = ir.extent(rank-1-i); }
443  if ( (! lower_bounds.empty()) && ( lower_bounds.size() != rank ) ) yakl_throw("ERROR: Passed lower bounds of the wrong rank");
444  for (int i=0; i < rank; i++) { this->lbounds[i] = lower_bounds[i]; }
445  }
446 
447 
450  template <class TLOC = T>
452  std::array<size_t,rank> dimensions;
453  for (int i=0; i < rank; i++) { dimensions[i] = this->dimension[rank-1-i]; }
454  if (myMem == memHost) {
455  return array_ir::ArrayIR<TLOC,rank>(const_cast<TLOC *>(this->myData),dimensions,array_ir::MEMORY_HOST,this->label());
456  } else {
457  #ifdef YAKL_MANAGED_MEMORY
458  return array_ir::ArrayIR<TLOC,rank>(const_cast<TLOC *>(this->myData),dimensions,array_ir::MEMORY_SHARED,this->label());
459  #else
460  return array_ir::ArrayIR<TLOC,rank>(const_cast<TLOC *>(this->myData),dimensions,array_ir::MEMORY_DEVICE,this->label());
461  #endif
462  }
463  }
464 
465 
466  // Common detailed documentation for all indexers
475  /* ARRAY INDEXERS (FORTRAN index ordering)
476  Return the element at the given index (either read-only or read-write)
477  */
480  YAKL_INLINE T &operator()(int i0) const {
481  static_assert( rank == 1 , "ERROR: Indexing non-rank-1 array with 1 index" );
482  #ifdef YAKL_DEBUG
483  check(i0);
484  #endif
485  index_t ind = (i0-this->lbounds[0]);
486  return this->myData[ind];
487  }
490  YAKL_INLINE T &operator()(int i0, int i1) const {
491  static_assert( rank == 2 , "ERROR: Indexing non-rank-2 array with 2 indices" );
492  #ifdef YAKL_DEBUG
493  check(i0,i1);
494  #endif
495  index_t ind = (i1-this->lbounds[1]) *
496  this->dimension[0] + (i0-this->lbounds[0]) ;
497  return this->myData[ind];
498  }
501  YAKL_INLINE T &operator()(int i0, int i1, int i2) const {
502  static_assert( rank == 3 , "ERROR: Indexing non-rank-3 array with 3 indices" );
503  #ifdef YAKL_DEBUG
504  check(i0,i1,i2);
505  #endif
506  index_t ind = ( (i2-this->lbounds[2]) *
507  this->dimension[1] + (i1-this->lbounds[1]) )*
508  this->dimension[0] + (i0-this->lbounds[0]) ;
509  return this->myData[ind];
510  }
513  YAKL_INLINE T &operator()(int i0, int i1, int i2, int i3) const {
514  static_assert( rank == 4 , "ERROR: Indexing non-rank-4 array with 4 indices" );
515  #ifdef YAKL_DEBUG
516  check(i0,i1,i2,i3);
517  #endif
518  index_t ind = (( (i3-this->lbounds[3]) *
519  this->dimension[2] + (i2-this->lbounds[2]) )*
520  this->dimension[1] + (i1-this->lbounds[1]) )*
521  this->dimension[0] + (i0-this->lbounds[0]) ;
522  return this->myData[ind];
523  }
526  YAKL_INLINE T &operator()(int i0, int i1, int i2, int i3, int i4) const {
527  static_assert( rank == 5 , "ERROR: Indexing non-rank-5 array with 5 indices" );
528  #ifdef YAKL_DEBUG
529  check(i0,i1,i2,i3,i4);
530  #endif
531  index_t ind = ((( (i4-this->lbounds[4]) *
532  this->dimension[3] + (i3-this->lbounds[3]) )*
533  this->dimension[2] + (i2-this->lbounds[2]) )*
534  this->dimension[1] + (i1-this->lbounds[1]) )*
535  this->dimension[0] + (i0-this->lbounds[0]) ;
536  return this->myData[ind];
537  }
540  YAKL_INLINE T &operator()(int i0, int i1, int i2, int i3, int i4, int i5) const {
541  static_assert( rank == 6 , "ERROR: Indexing non-rank-6 array with 6 indices" );
542  #ifdef YAKL_DEBUG
543  check(i0,i1,i2,i3,i4,i5);
544  #endif
545  index_t ind = (((( (i5-this->lbounds[5]) *
546  this->dimension[4] + (i4-this->lbounds[4]) )*
547  this->dimension[3] + (i3-this->lbounds[3]) )*
548  this->dimension[2] + (i2-this->lbounds[2]) )*
549  this->dimension[1] + (i1-this->lbounds[1]) )*
550  this->dimension[0] + (i0-this->lbounds[0]) ;
551  return this->myData[ind];
552  }
555  YAKL_INLINE T &operator()(int i0, int i1, int i2, int i3, int i4, int i5, int i6) const {
556  static_assert( rank == 7 , "ERROR: Indexing non-rank-7 array with 7 indices" );
557  #ifdef YAKL_DEBUG
558  check(i0,i1,i2,i3,i4,i5,i6);
559  #endif
560  index_t ind = ((((( (i6-this->lbounds[6]) *
561  this->dimension[5] + (i5-this->lbounds[5]) )*
562  this->dimension[4] + (i4-this->lbounds[4]) )*
563  this->dimension[3] + (i3-this->lbounds[3]) )*
564  this->dimension[2] + (i2-this->lbounds[2]) )*
565  this->dimension[1] + (i1-this->lbounds[1]) )*
566  this->dimension[0] + (i0-this->lbounds[0]) ;
567  return this->myData[ind];
568  }
571  YAKL_INLINE T &operator()(int i0, int i1, int i2, int i3, int i4, int i5, int i6, int i7) const {
572  static_assert( rank == 8 , "ERROR: Indexing non-rank-8 array with 8 indices" );
573  #ifdef YAKL_DEBUG
574  check(i0,i1,i2,i3,i4,i5,i6,i7);
575  #endif
576  index_t ind = (((((( (i7-this->lbounds[7]) *
577  this->dimension[6] + (i6-this->lbounds[6]) )*
578  this->dimension[5] + (i5-this->lbounds[5]) )*
579  this->dimension[4] + (i4-this->lbounds[4]) )*
580  this->dimension[3] + (i3-this->lbounds[3]) )*
581  this->dimension[2] + (i2-this->lbounds[2]) )*
582  this->dimension[1] + (i1-this->lbounds[1]) )*
583  this->dimension[0] + (i0-this->lbounds[0]) ;
584  return this->myData[ind];
585  }
586 
587 
589  YAKL_INLINE void check(int i0, int i1=1, int i2=1, int i3=1, int i4=1, int i5=1,
590  int i6=1, int i7=1) const {
591  #ifdef YAKL_DEBUG
592  if (! this->initialized()) { yakl_throw("Error: Using operator() on an Array that isn't allocated"); }
593  if constexpr (rank >= 1) { if (i0 < this->lbounds[0] || i0 >= this->lbounds[0]+this->dimension[0]) ind_out_bounds<0>(i0); }
594  if constexpr (rank >= 2) { if (i1 < this->lbounds[1] || i1 >= this->lbounds[1]+this->dimension[1]) ind_out_bounds<1>(i1); }
595  if constexpr (rank >= 3) { if (i2 < this->lbounds[2] || i2 >= this->lbounds[2]+this->dimension[2]) ind_out_bounds<2>(i2); }
596  if constexpr (rank >= 4) { if (i3 < this->lbounds[3] || i3 >= this->lbounds[3]+this->dimension[3]) ind_out_bounds<3>(i3); }
597  if constexpr (rank >= 5) { if (i4 < this->lbounds[4] || i4 >= this->lbounds[4]+this->dimension[4]) ind_out_bounds<4>(i4); }
598  if constexpr (rank >= 6) { if (i5 < this->lbounds[5] || i5 >= this->lbounds[5]+this->dimension[5]) ind_out_bounds<5>(i5); }
599  if constexpr (rank >= 7) { if (i6 < this->lbounds[6] || i6 >= this->lbounds[6]+this->dimension[6]) ind_out_bounds<6>(i6); }
600  if constexpr (rank >= 8) { if (i7 < this->lbounds[7] || i7 >= this->lbounds[7]+this->dimension[7]) ind_out_bounds<7>(i7); }
601  #if defined(YAKL_SEPARATE_MEMORY_SPACE)
602  YAKL_EXECUTE_ON_DEVICE_ONLY( if constexpr (myMem == memHost) yakl_throw("ERROR: host array being accessed in a device kernel"); )
603  #if !defined(YAKL_MANAGED_MEMORY)
605  if constexpr (myMem == memDevice) {
606  std::cerr << "ERROR: For Array labeled: " << this->myname << ":" << std::endl;
607  yakl_throw("Device array being accessed on the host without managed memory turned on");
608  }
609  )
610  #endif
611  #endif
612  #endif
613  }
614 
615 
616  // if this function gets called, then there was definitely an error
618  template <int I>
619  YAKL_INLINE void ind_out_bounds(int ind) const {
620  #ifdef YAKL_DEBUG
622  std::cerr << "ERROR: For Array labeled: " << this->myname << ":" << std::endl;
623  std::cerr << "Index " << I+1 << " of " << rank << " is out of bounds. Provided index: " << ind
624  << ". Lower Bound: " << this->lbounds[I] << ". Upper Bound: " << this->dimension[I]-1 << std::endl;
625  )
626  yakl_throw("ERROR: Index out of bounds.");
627  #endif
628  }
629 
630 
632  template <class TLOC, typename std::enable_if<std::is_arithmetic<TLOC>::value,bool>::type = false>
633  Array operator=(TLOC const &rhs) const {
634  memset_loc(rhs);
635  return *this;
636  }
637 
638 
640  template <class TLOC>
641  void memset_loc(TLOC rhs) const {
642  if (myMem == memDevice) {
643  #ifdef YAKL_ENABLE_STREAMS
644  fence();
645  #endif
646  memset(*this, rhs);
647  #ifdef YAKL_ENABLE_STREAMS
648  fence();
649  #endif
650  } else {
651  for (int i=0; i < this->totElems(); i++) { this->myData[i] = rhs; }
652  }
653  }
654 
655 
659 
660 
663  #ifdef YAKL_DEBUG
664  if (! this->initialized()) { yakl_throw("ERROR: Trying to subset_slowest_dimension an Array that hasn't been initialized"); }
665  if (l < lbounds[rank-1]) { yakl_throw("ERROR: subset_slowest_dimension lower bound too low"); }
666  if (u < lbounds[rank-1]) { yakl_throw("ERROR: subset_slowest_dimension upper bound too low"); }
667  if (l > u) { yakl_throw("ERROR: subset_slowest_dimension lower bound > upper bounds"); }
668  if (u >= this->lbounds[rank-1]+this->dimension[rank-1]) { yakl_throw("ERROR: subset_slowest_dimension upper bound too high"); }
669  #endif
670  auto ret = *this;
671  auto &lb = this->lbounds;
672  auto &d = this->dimension;
673  if constexpr (rank == 1) ret.myData += (l-lb[rank-1]);
674  if constexpr (rank == 2) ret.myData += (l-lb[rank-1])*d[0];
675  if constexpr (rank == 3) ret.myData += (l-lb[rank-1])*d[0]*d[1];
676  if constexpr (rank == 4) ret.myData += (l-lb[rank-1])*d[0]*d[1]*d[2];
677  if constexpr (rank == 5) ret.myData += (l-lb[rank-1])*d[0]*d[1]*d[2]*d[3];
678  if constexpr (rank == 6) ret.myData += (l-lb[rank-1])*d[0]*d[1]*d[2]*d[3]*d[4];
679  if constexpr (rank == 7) ret.myData += (l-lb[rank-1])*d[0]*d[1]*d[2]*d[3]*d[4]*d[5];
680  if constexpr (rank == 8) ret.myData += (l-lb[rank-1])*d[0]*d[1]*d[2]*d[3]*d[4]*d[5]*d[6];
681  ret.dimension[rank-1] = u-l+1;
682  return ret;
683  }
684 
685 
710  template <int N> YAKL_INLINE Array<T,N,myMem,styleFortran> slice( Dims const &dims ) const {
711  #ifdef YAKL_DEBUG
712  if (rank != dims.size()) {
713  YAKL_EXECUTE_ON_HOST_ONLY( std::cerr << "For Array named " << this->myname << ": "; )
714  yakl_throw("ERROR: rank must be equal to dims.size()");
715  }
716  for (int i=N; i<rank; i++) {
717  if (dims.data[i] < this->lbounds[i] || dims.data[i] >= this->lbounds[i]+this->dimension[i] ) {
718  YAKL_EXECUTE_ON_HOST_ONLY( std::cerr << "For Array named " << this->myname << ": "; )
719  yakl_throw("ERROR: One of the slicing dimension dimensions is out of bounds");
720  }
721  }
722  if (! this->initialized()) {
723  YAKL_EXECUTE_ON_HOST_ONLY( std::cerr << "For Array named " << this->myname << ": "; )
724  yakl_throw("ERROR: calling slice() on an Array that hasn't been allocated");
725  }
726  #endif
728  index_t offset = 1;
729  for (int i=0; i<N; i++) {
730  ret.dimension[i] = this->dimension[i];
731  ret.lbounds [i] = this->lbounds [i];
732  offset *= this->dimension[i];
733  }
734  index_t retOff = 0;
735  for (int i=N; i<rank; i++) {
736  retOff += (dims.data[i]-this->lbounds[i])*offset;
737  offset *= this->dimension[i];
738  }
739  ret.myData = &(this->myData[retOff]);
741  yakl_mtx_lock();
742  ret.refCount = this->refCount;
743  if (this->refCount != nullptr) {
744  (*(this->refCount))++;
745  }
746  yakl_mtx_unlock();
747  )
748  return ret;
749  }
752  template <int N> YAKL_INLINE Array<T,N,myMem,styleFortran> slice( int i0 ) const {
753  static_assert( rank == 1 , "ERROR: Calling slice() with 1 index on a non-rank-1 array" );
754  static_assert( N <= rank , "ERROR: Calling slice() with more dimenions than this array's rank" );
755  return slice<N>( Dims(i0) );
756  }
759  template <int N> YAKL_INLINE Array<T,N,myMem,styleFortran> slice( int i0, int i1 ) const {
760  static_assert( rank == 2 , "ERROR: Calling slice() with 2 index on a non-rank-2 array" );
761  static_assert( N <= rank , "ERROR: Calling slice() with more dimenions than this array's rank" );
762  return slice<N>( Dims(i0,i1) );
763  }
766  template <int N> YAKL_INLINE Array<T,N,myMem,styleFortran> slice( int i0, int i1, int i2 ) const {
767  static_assert( rank == 3 , "ERROR: Calling slice() with 3 index on a non-rank-3 array" );
768  static_assert( N <= rank , "ERROR: Calling slice() with more dimenions than this array's rank" );
769  return slice<N>( Dims(i0,i1,i2) );
770  }
773  template <int N> YAKL_INLINE Array<T,N,myMem,styleFortran> slice( int i0, int i1, int i2, int i3 ) const {
774  static_assert( rank == 4 , "ERROR: Calling slice() with 4 index on a non-rank-4 array" );
775  static_assert( N <= rank , "ERROR: Calling slice() with more dimenions than this array's rank" );
776  return slice<N>( Dims(i0,i1,i2,i3) );
777  }
780  template <int N> YAKL_INLINE Array<T,N,myMem,styleFortran> slice( int i0, int i1, int i2, int i3,
781  int i4 ) const {
782  static_assert( rank == 5 , "ERROR: Calling slice() with 5 index on a non-rank-5 array" );
783  static_assert( N <= rank , "ERROR: Calling slice() with more dimenions than this array's rank" );
784  return slice<N>( Dims(i0,i1,i2,i3,i4) );
785  }
788  template <int N> YAKL_INLINE Array<T,N,myMem,styleFortran> slice( int i0, int i1, int i2, int i3,
789  int i4, int i5 ) const {
790  static_assert( rank == 6 , "ERROR: Calling slice() with 6 index on a non-rank-6 array" );
791  static_assert( N <= rank , "ERROR: Calling slice() with more dimenions than this array's rank" );
792  return slice<N>( Dims(i0,i1,i2,i3,i4,i5) );
793  }
796  template <int N> YAKL_INLINE Array<T,N,myMem,styleFortran> slice( int i0, int i1, int i2, int i3,
797  int i4, int i5, int i6 ) const {
798  static_assert( rank == 7 , "ERROR: Calling slice() with 7 index on a non-rank-7 array" );
799  static_assert( N <= rank , "ERROR: Calling slice() with more dimenions than this array's rank" );
800  return slice<N>( Dims(i0,i1,i2,i3,i4,i5,i6) );
801  }
804  template <int N> YAKL_INLINE Array<T,N,myMem,styleFortran> slice( int i0, int i1, int i2, int i3,
805  int i4, int i5, int i6, int i7 ) const {
806  static_assert( rank == 8 , "ERROR: Calling slice() with 8 index on a non-rank-8 array" );
807  static_assert( N <= rank , "ERROR: Calling slice() with more dimenions than this array's rank" );
808  return slice<N>( Dims(i0,i1,i2,i3,i4,i5,i6,i7) );
809  }
810 
811 
812 
838  template <int N> YAKL_INLINE Array<T,N,myMem,styleFortran> reshape(Bnds const &bnds) const {
839  #ifdef YAKL_DEBUG
840  if (! this->initialized()) { yakl_throw("ERROR: Trying to reshape an Array that hasn't been initialized"); }
841  if (bnds.size() != N) { yakl_throw("ERROR: new number of reshaped array dimensions does not match the templated rank"); }
842  index_t totelems = 1;
843  for (int i=0; i < N; i++) { totelems *= (bnds.u[i]-bnds.l[i]+1); }
844  if (totelems != this->totElems()) { yakl_throw("ERROR: Total number of reshaped array elements is not consistent with this array"); }
845  #endif
847  for (int i=0; i < N; i++) {
848  ret.dimension[i] = bnds.u[i] - bnds.l[i] + 1; ret.lbounds [i] = bnds.l[i];
849  }
850  #ifdef YAKL_DEBUG
851  ret.myname = this->myname;
852  #endif
853  ret.myData = this->myData;
855  yakl_mtx_lock();
856  ret.refCount = this->refCount;
857  if (this->refCount != nullptr) {
858  (*(this->refCount))++;
859  }
860  yakl_mtx_unlock();
861  )
862  return ret;
863  }
866  YAKL_INLINE Array<T,1,myMem,styleFortran> reshape(Bnd b0 ) const { return reshape<1>( Bnds(b0) ); }
869  YAKL_INLINE Array<T,2,myMem,styleFortran> reshape(Bnd b0, Bnd b1 ) const { return reshape<2>( Bnds(b0,b1) ); }
872  YAKL_INLINE Array<T,3,myMem,styleFortran> reshape(Bnd b0, Bnd b1, Bnd b2 ) const { return reshape<3>( Bnds(b0,b1,b2) ); }
875  YAKL_INLINE Array<T,4,myMem,styleFortran> reshape(Bnd b0, Bnd b1, Bnd b2, Bnd b3 ) const { return reshape<4>( Bnds(b0,b1,b2,b3) ); }
878  YAKL_INLINE Array<T,5,myMem,styleFortran> reshape(Bnd b0, Bnd b1, Bnd b2, Bnd b3, Bnd b4 ) const { return reshape<5>( Bnds(b0,b1,b2,b3,b4) ); }
881  YAKL_INLINE Array<T,6,myMem,styleFortran> reshape(Bnd b0, Bnd b1, Bnd b2, Bnd b3, Bnd b4, Bnd b5 ) const { return reshape<6>( Bnds(b0,b1,b2,b3,b4,b5) ); }
884  YAKL_INLINE Array<T,7,myMem,styleFortran> reshape(Bnd b0, Bnd b1, Bnd b2, Bnd b3, Bnd b4, Bnd b5, Bnd b6 ) const { return reshape<7>( Bnds(b0,b1,b2,b3,b4,b5,b6) ); }
887  YAKL_INLINE Array<T,8,myMem,styleFortran> reshape(Bnd b0, Bnd b1, Bnd b2, Bnd b3, Bnd b4, Bnd b5, Bnd b6, Bnd b7) const { return reshape<8>( Bnds(b0,b1,b2,b3,b4,b5,b6,b7) ); }
888 
889 
903  #ifdef YAKL_DEBUG
904  if (! this->initialized()) { yakl_throw("ERROR: Trying to collapse an Array that hasn't been initialized"); }
905  #endif
907  ret.dimension[0] = this->totElems(); ret.lbounds [0] = lbnd;
908  #ifdef YAKL_DEBUG
909  ret.myname = this->myname;
910  #endif
911  ret.myData = this->myData;
913  yakl_mtx_lock();
914  ret.refCount = this->refCount;
915  if (this->refCount != nullptr) {
916  (*(this->refCount))++;
917  }
918  yakl_mtx_unlock();
919  )
920  return ret;
921  }
922 
923 
924  // Create a host copy of this array. Even if the array exists on the host, a deep copy to a separate
925  // object is still performed to avoid any potential bugs when the user expects this behavior
937  template <class TLOC=T>
939  auto ret = createHostObject();
940  this->copy_inform(ret);
941  if (myMem == memHost) { memcpy_host_to_host ( ret.myData , this->myData , this->totElems() ); }
942  else { memcpy_device_to_host( ret.myData , this->myData , this->totElems() , stream ); }
943  if (stream.is_default_stream()) { fence(); }
944  else { stream.fence(); }
946  }
947 
948 
949  // Create a separate host Array with the same rank memory space and style
956  template <class TLOC=typename std::remove_cv<T>::type>
958  #ifdef YAKL_DEBUG
959  if (! this->initialized()) {
960  YAKL_EXECUTE_ON_HOST_ONLY( std::cerr << "For Array named " << this->myname << ": "; )
961  yakl_throw("Error: createHostCopy() called on an Array that hasn't been allocated.");
962  }
963  #endif
964  // If this Array is of const type, then we need to use non-const when allocating, then cast it to const aterward
965  Array<typename std::remove_cv<TLOC>::type,rank,memHost,styleFortran> ret; // nullified + owned == true
966  for (int i=0; i<rank; i++) { ret.lbounds[i] = this->lbounds[i]; ret.dimension[i] = this->dimension[i]; }
967  #ifdef YAKL_DEBUG
968  ret.myname = this->myname;
969  #endif
970  ret.allocate();
971  return ret;
972  }
973 
974 
975  // Create a device copy of this array. Even if the array exists on the host, a deep copy to a separate
976  // object is still performed to avoid any potential bugs when the user expects this behavior
988  template <class TLOC=T>
990  auto ret = createDeviceObject();
991  this->copy_inform(ret);
992  if (myMem == memHost) { memcpy_host_to_device ( ret.myData , this->myData , this->totElems() , stream ); }
993  else { memcpy_device_to_device( ret.myData , this->myData , this->totElems() , stream ); }
994  if (stream.is_default_stream()) { fence(); }
995  else { stream.fence(); }
997  }
998 
999 
1000  // Create separate device array with the same rank, memory space, and style
1007  template <class TLOC=typename std::remove_cv<T>::type>
1009  #ifdef YAKL_DEBUG
1010  if (! this->initialized()) {
1011  YAKL_EXECUTE_ON_HOST_ONLY( std::cerr << "For Array named " << this->myname << ": "; )
1012  yakl_throw("Error: createHostCopy() called on an Array that hasn't been allocated.");
1013  }
1014  #endif
1015  // If this Array is of const type, then we need to use non-const when allocating, then cast it to const aterward
1016  Array<typename std::remove_cv<TLOC>::type,rank,memDevice,styleFortran> ret; // nullified + owned == true
1017  for (int i=0; i<rank; i++) { ret.lbounds[i] = this->lbounds[i]; ret.dimension[i] = this->dimension[i]; }
1018  #ifdef YAKL_DEBUG
1019  ret.myname = this->myname;
1020  #endif
1021  ret.allocate();
1022  return ret;
1023  }
1024 
1025 
1026  /* ACCESSORS */
1032  for (int i=0; i<rank; i++) { ret(i+1) = this->dimension[i]; }
1033  return ret;
1034  }
1040  for (int i=0; i<rank; i++) { ret(i+1) = this->lbounds[i]; }
1041  return ret;
1042  }
1048  for (int i=0; i<rank; i++) { ret(i+1) = this->lbounds[i]+this->dimension[i]-1; }
1049  return ret;
1050  }
1054  YAKL_INLINE index_t extent( int dim ) const {
1055  #ifdef YAKL_DEBUG
1056  if (dim < 0 || dim > rank-1) yakl_throw("ERROR: calling extent() with an out of bounds index");
1057  #endif
1058  return this->dimension[dim];
1059  }
1060 
1061  };
1062 
1063 }
1065 
1066 
yakl::Array< T, rank, myMem, styleFortran >::Array
YAKL_INLINE Array(char const *label, T *data, Bnd b1)
1-D non-owned constructor
Definition: YAKL_FArray.h:234
yakl::Array< T, rank, myMem, styleFortran >::slice
YAKL_INLINE Array< T, N, myMem, styleFortran > slice(int i0) const
Array slice of 1-D array.
Definition: YAKL_FArray.h:752
yakl::Array< T, rank, myMem, styleFortran >::Array
YAKL_INLINE Array(Array< non_const_value_type, rank, myMem, styleFortran > const &rhs)
Copy metadata, share data pointer; if owned, increment reference counter. No deep copy.
Definition: YAKL_FArray.h:321
yakl::Array< T, rank, myMem, styleFortran >::get_dimensions
YAKL_INLINE FSArray< index_t, 1, SB< rank > > get_dimensions() const
Returns the dimensions of this array as a yakl::FSArray object.
Definition: YAKL_FArray.h:1030
YAKL_EXECUTE_ON_DEVICE_ONLY
#define YAKL_EXECUTE_ON_DEVICE_ONLY(...)
[NOT COMMONLY USED] Macro function used to determine if the current code is compiling for the device.
Definition: YAKL_defines.h:158
yakl::Bnds::size
YAKL_INLINE int size() const
Get the number of dimensions.
Definition: YAKL_Array.h:340
yakl::Array< T, rank, myMem, styleFortran >::get_lbounds
YAKL_INLINE FSArray< int, 1, SB< rank > > get_lbounds() const
Returns the lower bound of each dimension of this array as a yakl::FSArray object.
Definition: YAKL_FArray.h:1038
yakl::memDevice
constexpr int memDevice
Specifies a device memory address space for a yakl::Array object.
Definition: YAKL_memory_spaces.h:13
yakl::Array< T, rank, myMem, styleFortran >::Array
YAKL_INLINE Array(char const *label, T *data, Bnd b1, Bnd b2, Bnd b3, Bnd b4, Bnd b5, Bnd b6, Bnd b7, Bnd b8)
8-D non-owned constructor
Definition: YAKL_FArray.h:290
array_ir::MEMORY_SHARED
constexpr int MEMORY_SHARED
Declares that the data pointer is defined in both host and device memory.
Definition: ArrayIR.h:18
yakl::Array< T, rank, myMem, styleFortran >::operator=
YAKL_INLINE Array & operator=(Array &&rhs)
Move metadata and data pointer. No deep copy.
Definition: YAKL_FArray.h:401
yakl::Array< T, rank, myMem, styleFortran >::create_ArrayIR
array_ir::ArrayIR< TLOC, rank > create_ArrayIR() const
Create an ArrayIR object from this FArray object for easy interoperability with other C++ portability...
Definition: YAKL_FArray.h:451
yakl::Array< T, rank, myMem, styleFortran >::reshape
YAKL_INLINE Array< T, 7, myMem, styleFortran > reshape(Bnd b0, Bnd b1, Bnd b2, Bnd b3, Bnd b4, Bnd b5, Bnd b6) const
Reshape array into a 7-D array.
Definition: YAKL_FArray.h:884
yakl::Array< T, rank, myMem, styleFortran >::Array
YAKL_INLINE Array(char const *label, T *data, Bnd b1, Bnd b2, Bnd b3, Bnd b4, Bnd b5)
5-D non-owned constructor
Definition: YAKL_FArray.h:260
yakl::Array< T, rank, myMem, styleFortran >::createDeviceCopy
Array< TLOC, rank, memDevice, styleFortran > createDeviceCopy(Stream stream=Stream()) const
[DEEP_COPY] Create a copy of this array in yakl::memDevice space
Definition: YAKL_FArray.h:989
yakl::Array< T, rank, myMem, styleFortran >::Array
YAKL_INLINE Array(char const *label, Bnd b1)
1-D owned constructor
Definition: YAKL_FArray.h:124
yakl::Array< T, rank, myMem, styleFortran >::Array
YAKL_INLINE Array(Array &&rhs)
Move metadata and data pointer. No deep copy.
Definition: YAKL_FArray.h:383
yakl::Array< T, rank, myMem, styleFortran >::Array
YAKL_INLINE Array(char const *label, Bnds bnds)
Generic initializer-list or std::vector based owned constructor.
Definition: YAKL_FArray.h:192
yakl::Stream
Implements the functionality of a stream for parallel kernel execution. If the Stream::create() metho...
Definition: YAKL_streams_events.h:394
yakl::Array< T, rank, myMem, styleFortran >::Array
YAKL_INLINE Array(char const *label, Bnd b1, Bnd b2, Bnd b3, Bnd b4, Bnd b5, Bnd b6, Bnd b7, Bnd b8)
8-D owned constructor
Definition: YAKL_FArray.h:180
yakl::Array< T, rank, myMem, styleFortran >::operator()
YAKL_INLINE T & operator()(int i0, int i1, int i2, int i3) const
Return reference to element at the requested index (4-D)
Definition: YAKL_FArray.h:513
yakl::Array< T, rank, myMem, styleFortran >::createDeviceObject
Array< typename std::remove_cv< TLOC >::type, rank, memDevice, styleFortran > createDeviceObject() const
Create and allocate a yakl::memDevice array object of the same type, rank, dimensions,...
Definition: YAKL_FArray.h:1008
yakl::Array< T, rank, myMem, styleFortran >::reshape
YAKL_INLINE Array< T, N, myMem, styleFortran > reshape(Bnds const &bnds) const
Reshape array using initializer list or std::vector indices.
Definition: YAKL_FArray.h:838
yakl::Array< T, rank, myMem, styleFortran >::operator()
YAKL_INLINE T & operator()(int i0, int i1) const
Return reference to element at the requested index (2-D)
Definition: YAKL_FArray.h:490
yakl::Array< T, rank, myMem, styleFortran >::createHostCopy
Array< TLOC, rank, memHost, styleFortran > createHostCopy(Stream stream=Stream()) const
[DEEP_COPY] Create a copy of this array in yakl::memHost space
Definition: YAKL_FArray.h:938
yakl::Array< T, rank, myMem, styleFortran >::Array
YAKL_INLINE Array(char const *label, Bnd b1, Bnd b2, Bnd b3, Bnd b4)
4-D owned constructor
Definition: YAKL_FArray.h:142
yakl::Array< T, rank, myMem, styleFortran >::createHostObject
Array< typename std::remove_cv< TLOC >::type, rank, memHost, styleFortran > createHostObject() const
Create and allocate a yakl::memHost array object of the same type, rank, dimensions,...
Definition: YAKL_FArray.h:957
yakl::Array< T, rank, myMem, styleFortran >::value_type
T value_type
This is the type T exactly as it was defined upon array object creation.
Definition: YAKL_FArray.h:61
yakl::Array< T, rank, myMem, styleFortran >::extent
YAKL_INLINE index_t extent(int dim) const
Returns the extent of the requested dimension of this array.
Definition: YAKL_FArray.h:1054
__YAKL_NAMESPACE_WRAPPER_END__
#define __YAKL_NAMESPACE_WRAPPER_END__
Definition: YAKL.h:20
yakl::Array< T, rank, myMem, styleFortran >::slice
YAKL_INLINE Array< T, N, myMem, styleFortran > slice(int i0, int i1, int i2, int i3, int i4, int i5, int i6, int i7) const
Array slice of 8-D array.
Definition: YAKL_FArray.h:804
yakl::Array< T, rank, myMem, styleFortran >::Array
YAKL_INLINE Array(char const *label)
Create an empty, unallocated object with a label.
Definition: YAKL_FArray.h:92
yakl::Array< T, rank, myMem, styleFortran >::Array
YAKL_INLINE Array(char const *label, Bnd b1, Bnd b2, Bnd b3)
3-D owned constructor
Definition: YAKL_FArray.h:135
array_ir::MEMORY_HOST
constexpr int MEMORY_HOST
Declares that the data pointer is defined only in host memory.
Definition: ArrayIR.h:14
yakl::memcpy_host_to_device
void memcpy_host_to_device(T1 *dst, T2 *src, index_t elems, Stream stream=Stream())
[USE AT YOUR OWN RISK]: memcpy the specified number of elements from host to device
Definition: YAKL_mem_transfers.h:85
yakl::Array< T, rank, myMem, styleFortran >::Array
YAKL_INLINE Array(char const *label, T *data, Bnd b1, Bnd b2, Bnd b3, Bnd b4, Bnd b5, Bnd b6, Bnd b7)
7-D non-owned constructor
Definition: YAKL_FArray.h:279
yakl::Array< T, rank, myMem, styleFortran >::Array
YAKL_INLINE Array()
Create an empty, unallocated object.
Definition: YAKL_FArray.h:88
yakl::Array< T, rank, myMem, styleFortran >::operator=
Array operator=(TLOC const &rhs) const
[ASYNCHRONOUS] Assign a scalar arithmetic value to all entries in this array object
Definition: YAKL_FArray.h:633
yakl::Array< T, rank, myMem, styleFortran >::Array
YAKL_INLINE Array(char const *label, T *data, Bnd b1, Bnd b2, Bnd b3, Bnd b4)
4-D non-owned constructor
Definition: YAKL_FArray.h:252
array_ir::MEMORY_DEVICE
constexpr int MEMORY_DEVICE
Declares that the data pointer is defined only in device memory.
Definition: ArrayIR.h:16
yakl::Array< T, rank, myMem, styleFortran >::reshape
YAKL_INLINE Array< T, 6, myMem, styleFortran > reshape(Bnd b0, Bnd b1, Bnd b2, Bnd b3, Bnd b4, Bnd b5) const
Reshape array into a 6-D array.
Definition: YAKL_FArray.h:881
yakl::Array< T, rank, myMem, styleFortran >::slice
YAKL_INLINE Array< T, N, myMem, styleFortran > slice(int i0, int i1, int i2, int i3, int i4, int i5) const
Array slice of 6-D array.
Definition: YAKL_FArray.h:788
yakl::Array< T, rank, myMem, styleFortran >::slice
YAKL_INLINE Array< T, N, myMem, styleFortran > slice(int i0, int i1) const
Array slice of 2-D array.
Definition: YAKL_FArray.h:759
yakl::Array< T, rank, myMem, styleFortran >::subset_slowest_dimension
YAKL_INLINE Array< T, rank, myMem, styleFortran > subset_slowest_dimension(int l, int u) const
Return an array aliasing a contiguous subset of the slowest dimension.
Definition: YAKL_FArray.h:662
__YAKL_NAMESPACE_WRAPPER_BEGIN__
#define __YAKL_NAMESPACE_WRAPPER_BEGIN__
Definition: YAKL.h:19
yakl::Array< T, rank, myMem, styleFortran >::reshape
YAKL_INLINE Array< T, 3, myMem, styleFortran > reshape(Bnd b0, Bnd b1, Bnd b2) const
Reshape array into a 3-D array.
Definition: YAKL_FArray.h:872
yakl::Array< T, rank, myMem, styleFortran >::~Array
YAKL_INLINE ~Array()
If owned, decrement reference counter, and deallocate data when it reaches zero. If non-owned,...
Definition: YAKL_FArray.h:425
yakl::Array< T, rank, myMem, styleFortran >::Array
YAKL_INLINE Array(char const *label, T *data, Bnd b1, Bnd b2)
2-D non-owned constructor
Definition: YAKL_FArray.h:239
yakl::Bnd
Describes a single bound for creating Fortran-style yakl::Array objects.
Definition: YAKL_Array.h:177
YAKL_INLINE
#define YAKL_INLINE
Used to decorate functions called from kernels (parallel_for and parallel_outer) or from CPU function...
Definition: YAKL_defines.h:140
yakl::Array< T, rank, myMem, styleFortran >::reshape
YAKL_INLINE Array< T, 8, myMem, styleFortran > reshape(Bnd b0, Bnd b1, Bnd b2, Bnd b3, Bnd b4, Bnd b5, Bnd b6, Bnd b7) const
Reshape array into a 8-D array.
Definition: YAKL_FArray.h:887
array_ir::ArrayIR
The ArrayIR class holds library-agnostic Array metadata to make it easy to transfer array objects bet...
Definition: ArrayIR.h:39
yakl::Array< T, rank, myMem, styleFortran >::Array
YAKL_INLINE Array(char const *label, Bnd b1, Bnd b2, Bnd b3, Bnd b4, Bnd b5)
5-D owned constructor
Definition: YAKL_FArray.h:150
yakl::Array< T, rank, myMem, styleFortran >::Array
YAKL_INLINE Array(char const *label, Bnd b1, Bnd b2, Bnd b3, Bnd b4, Bnd b5, Bnd b6)
6-D owned constructor
Definition: YAKL_FArray.h:159
yakl::Dims::size
YAKL_INLINE int size() const
Get the number of dimensions.
Definition: YAKL_Array.h:166
yakl::fence
void fence()
Block the host code until all device code has completed.
Definition: YAKL_fence.h:16
yakl::Array< T, rank, myMem, styleFortran >::slice
YAKL_INLINE Array< T, N, myMem, styleFortran > slice(int i0, int i1, int i2) const
Array slice of 3-D array.
Definition: YAKL_FArray.h:766
yakl::Array< T, rank, myMem, styleFortran >::operator()
YAKL_INLINE T & operator()(int i0) const
Return reference to element at the requested index (1-D)
Definition: YAKL_FArray.h:480
yakl::Array< T, rank, myMem, styleFortran >::get_ubounds
YAKL_INLINE FSArray< int, 1, SB< rank > > get_ubounds() const
Returns the upper bound of each dimension of this array as a yakl::FSArray object.
Definition: YAKL_FArray.h:1046
yakl::Array< T, rank, myMem, styleFortran >::collapse
YAKL_INLINE Array< T, 1, myMem, styleFortran > collapse(int lbnd=1) const
Collapse this array into a 1-D array.
Definition: YAKL_FArray.h:902
YAKL_EXECUTE_ON_HOST_ONLY
#define YAKL_EXECUTE_ON_HOST_ONLY(...)
[NOT COMMONLY USED] Macro function used to determine if the current code is compiling for the host.
Definition: YAKL_defines.h:153
yakl::index_t
unsigned int index_t
Definition: YAKL.h:41
yakl::Array< T, rank, myMem, styleFortran >::slice
YAKL_INLINE Array< T, N, myMem, styleFortran > slice(int i0, int i1, int i2, int i3, int i4) const
Array slice of 5-D array.
Definition: YAKL_FArray.h:780
yakl::Array< T, rank, myMem, styleFortran >::Array
YAKL_INLINE Array(Array< const_value_type, rank, myMem, styleFortran > const &rhs)
Copy metadata, share data pointer; if owned, increment reference counter. No deep copy.
Definition: YAKL_FArray.h:327
yakl::yakl_throw
YAKL_INLINE void yakl_throw(const char *msg)
Throw an error message. Works from the host or device.
Definition: YAKL_error.h:17
yakl::memcpy_host_to_host
void memcpy_host_to_host(T1 *dst, T2 *src, index_t elems)
[USE AT YOUR OWN RISK]: memcpy the specified number of elements on the host
Definition: YAKL_mem_transfers.h:20
yakl::Array< T, rank, myMem, styleFortran >
This implements the yakl:Array class with yakl::styleFortran behavior.
Definition: YAKL_FArray.h:55
array_ir::ArrayIR::label
const char * label() const
Get the label for this array.
Definition: ArrayIR.h:117
yakl::Array< T, rank, myMem, styleFortran >::const_value_type
std::add_const< type >::type const_value_type
This is the type T with const added to it.
Definition: YAKL_FArray.h:64
yakl::Dims
This class holds C-style dimensions for using in yakl::Array objects.
Definition: YAKL_Array.h:50
array_ir::ArrayIR::data_valid_on_device
bool data_valid_on_device() const
Determine if the data pointer is valid on the device.
Definition: ArrayIR.h:127
yakl::Array
This declares the yakl::Array class. Please see the yakl::styleC and yakl::styleFortran template spec...
Definition: YAKL_Array.h:40
yakl::memcpy_device_to_device
void memcpy_device_to_device(T1 *dst, T2 *src, index_t elems, Stream stream=Stream())
[USE AT YOUR OWN RISK]: memcpy the specified number of elements on the device
Definition: YAKL_mem_transfers.h:119
yakl::Array< T, rank, myMem, styleFortran >::Array
Array(array_ir::ArrayIR< T, rank > const &ir, std::vector< int > lower_bounds=std::vector< int >())
Construct this FArray object from an ArrayIR object for easy interoperability with other C++ portabil...
Definition: YAKL_FArray.h:434
yakl::Array< T, rank, myMem, styleFortran >::operator()
YAKL_INLINE T & operator()(int i0, int i1, int i2) const
Return reference to element at the requested index (3-D)
Definition: YAKL_FArray.h:501
yakl::Array< T, rank, myMem, styleFortran >::Array
YAKL_INLINE Array(char const *label, T *data, Bnd b1, Bnd b2, Bnd b3, Bnd b4, Bnd b5, Bnd b6)
6-D non-owned constructor
Definition: YAKL_FArray.h:269
yakl::Array< T, rank, myMem, styleFortran >::Array
YAKL_INLINE Array(char const *label, Bnd b1, Bnd b2, Bnd b3, Bnd b4, Bnd b5, Bnd b6, Bnd b7)
7-D owned constructor
Definition: YAKL_FArray.h:169
yakl::Array< T, rank, myMem, styleFortran >::operator()
YAKL_INLINE T & operator()(int i0, int i1, int i2, int i3, int i4, int i5, int i6) const
Return reference to element at the requested index (7-D)
Definition: YAKL_FArray.h:555
array_ir::ArrayIR::extent
size_t extent(int i) const
Get the extent of the dimension of the provided index.
Definition: ArrayIR.h:108
yakl::Array< T, rank, myMem, styleFortran >::slice
YAKL_INLINE Array< T, N, myMem, styleFortran > slice(int i0, int i1, int i2, int i3) const
Array slice of 4-D array.
Definition: YAKL_FArray.h:773
yakl::styleFortran
constexpr int styleFortran
Template parameter for yakl::Array that specifies it should follow Fortran-style behavior.
Definition: YAKL_Array.h:22
yakl
array_ir::ArrayIR::data
T * data() const
Get the data pointer.
Definition: ArrayIR.h:102
yakl::Array< T, rank, myMem, styleFortran >::slice
YAKL_INLINE Array< T, N, myMem, styleFortran > slice(int i0, int i1, int i2, int i3, int i4, int i5, int i6) const
Array slice of 7-D array.
Definition: YAKL_FArray.h:796
yakl::memcpy_device_to_host
void memcpy_device_to_host(T1 *dst, T2 *src, index_t elems, Stream stream=Stream())
[USE AT YOUR OWN RISK]: memcpy the specified number of elements from device to host
Definition: YAKL_mem_transfers.h:51
yakl::Array< T, rank, myMem, styleFortran >::non_const_value_type
std::remove_const< type >::type non_const_value_type
This is the type T with const removed from it.
Definition: YAKL_FArray.h:67
yakl::Array< T, rank, myMem, styleFortran >::Array
YAKL_INLINE Array(char const *label, T *data, Bnd b1, Bnd b2, Bnd b3)
3-D non-owned constructor
Definition: YAKL_FArray.h:245
yakl::Bnds
This class holds Fortran-style dimensions for using in creating yakl::Array objects.
Definition: YAKL_Array.h:200
array_ir::ArrayIR::data_valid_on_host
bool data_valid_on_host() const
Determine if the data pointer is valid on the host.
Definition: ArrayIR.h:125
yakl::Array< T, rank, myMem, styleFortran >::Array
YAKL_INLINE Array(char const *label, T *data, Bnds bnds)
Generic initializer-list or std::vector based owned constructor.
Definition: YAKL_FArray.h:302
yakl::Array< T, rank, myMem, styleFortran >::operator()
YAKL_INLINE T & operator()(int i0, int i1, int i2, int i3, int i4) const
Return reference to element at the requested index (5-D)
Definition: YAKL_FArray.h:526
yakl::Array< T, rank, myMem, styleFortran >::operator()
YAKL_INLINE T & operator()(int i0, int i1, int i2, int i3, int i4, int i5) const
Return reference to element at the requested index (6-D)
Definition: YAKL_FArray.h:540
yakl::Array< T, rank, myMem, styleFortran >::subset_slowest_dimension
YAKL_INLINE Array< T, rank, myMem, styleFortran > subset_slowest_dimension(int u) const
Return an array aliasing a contiguous subset of the slowest dimension. Retuns the same array with the...
Definition: YAKL_FArray.h:658
yakl::Array< T, rank, myMem, styleFortran >::slice
YAKL_INLINE Array< T, N, myMem, styleFortran > slice(Dims const &dims) const
Array slice using initializer list or std::vector indices.
Definition: YAKL_FArray.h:710
yakl::Array< T, rank, myMem, styleFortran >::operator()
YAKL_INLINE T & operator()(int i0, int i1, int i2, int i3, int i4, int i5, int i6, int i7) const
Return reference to element at the requested index (8-D)
Definition: YAKL_FArray.h:571
yakl::Array< T, rank, myMem, styleFortran >::reshape
YAKL_INLINE Array< T, 5, myMem, styleFortran > reshape(Bnd b0, Bnd b1, Bnd b2, Bnd b3, Bnd b4) const
Reshape array into a 5-D array.
Definition: YAKL_FArray.h:878
yakl::Array< T, rank, myMem, styleFortran >::operator=
YAKL_INLINE Array & operator=(Array< const_value_type, rank, myMem, styleFortran > const &rhs)
Copy metadata, share data pointer; if owned, increment reference counter. No deep copy.
Definition: YAKL_FArray.h:346
yakl::Array< T, rank, myMem, styleFortran >::Array
YAKL_INLINE Array(char const *label, Bnd b1, Bnd b2)
2-D owned constructor
Definition: YAKL_FArray.h:129
yakl::Array< T, rank, myMem, styleFortran >::reshape
YAKL_INLINE Array< T, 4, myMem, styleFortran > reshape(Bnd b0, Bnd b1, Bnd b2, Bnd b3) const
Reshape array into a 4-D array.
Definition: YAKL_FArray.h:875
yakl::ArrayBase
This class implements functionality common to both yakl::styleC and yakl::styleFortran Array objects.
Definition: YAKL_ArrayBase.h:24
yakl::Array< T, rank, myMem, styleFortran >::operator=
YAKL_INLINE Array & operator=(Array< non_const_value_type, rank, myMem, styleFortran > const &rhs)
Copy metadata, share data pointer; if owned, increment reference counter. No deep copy.
Definition: YAKL_FArray.h:337
yakl::Array< T, rank, myMem, styleFortran >::reshape
YAKL_INLINE Array< T, 1, myMem, styleFortran > reshape(Bnd b0) const
Reshape array into a 1-D array.
Definition: YAKL_FArray.h:866
yakl::Array< T, rank, myMem, styleFortran >::reshape
YAKL_INLINE Array< T, 2, myMem, styleFortran > reshape(Bnd b0, Bnd b1) const
Reshape array into a 2-D array.
Definition: YAKL_FArray.h:869
yakl::FSArray
Fortran-style array on the stack similar in nature to, e.g., float arr[ny][nx];
Definition: YAKL_FSArray.h:53
yakl::memHost
constexpr int memHost
Specifies a device memory address space for a yakl::Array object.
Definition: YAKL_memory_spaces.h:15
yakl::Array< T, rank, myMem, styleFortran >::type
std::remove_cv< T >::type type
This is the type T without const and volatile modifiers.
Definition: YAKL_FArray.h:59