codekingpro/portable-devtools
114k
1/*2//@HEADER3// ************************************************************************4//5// Kokkos v. 2.06// Copyright (2019) Sandia Corporation7//8// Under the terms of Contract DE-AC04-94AL85000 with Sandia Corporation,9// the U.S. Government retains certain rights in this software.10//11// Redistribution and use in source and binary forms, with or without12// modification, are permitted provided that the following conditions are13// met:14//15// 1. Redistributions of source code must retain the above copyright16// notice, this list of conditions and the following disclaimer.17//18// 2. Redistributions in binary form must reproduce the above copyright19// notice, this list of conditions and the following disclaimer in the20// documentation and/or other materials provided with the distribution.21//22// 3. Neither the name of the Corporation nor the names of the23// contributors may be used to endorse or promote products derived from24// this software without specific prior written permission.25//26// THIS SOFTWARE IS PROVIDED BY SANDIA CORPORATION "AS IS" AND ANY27// EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE28// IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR29// PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL SANDIA CORPORATION OR THE30// CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,31// EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,32// PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR33// PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF34// LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING35// NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS36// SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.37//38// Questions? Contact Christian R. Trott (crtrott@sandia.gov)39//40// ************************************************************************41//@HEADER42*/43 44 45#ifndef _LIBCUDACXX___MDSPAN_MDSPAN_HPP46#define _LIBCUDACXX___MDSPAN_MDSPAN_HPP47 48#ifndef __cuda_std__49#include <__config>50#endif // __cuda_std__51 52#include "../__mdspan/default_accessor.h"53#include "../__mdspan/layout_right.h"54#include "../__mdspan/extents.h"55#include "../__mdspan/compressed_pair.h"56#include "../__type_traits/extent.h"57#include "../__type_traits/is_constructible.h"58#include "../__type_traits/is_convertible.h"59#include "../__type_traits/is_default_constructible.h"60#include "../__type_traits/is_nothrow_constructible.h"61#include "../__type_traits/rank.h"62#include "../__type_traits/remove_cv.h"63#include "../__type_traits/remove_pointer.h"64#include "../__type_traits/remove_reference.h"65#include "../__type_traits/remove_all_extents.h"66#include "../__utility/as_const.h"67#include "../__utility/integer_sequence.h"68#include "../__utility/move.h"69#include "../array"70#include "../span"71 72#if defined(_CCCL_IMPLICIT_SYSTEM_HEADER_GCC)73# pragma GCC system_header74#elif defined(_CCCL_IMPLICIT_SYSTEM_HEADER_CLANG)75# pragma clang system_header76#elif defined(_CCCL_IMPLICIT_SYSTEM_HEADER_MSVC)77# pragma system_header78#endif // no system header79 80_LIBCUDACXX_BEGIN_NAMESPACE_STD81 82#if _LIBCUDACXX_STD_VER > 1183 84template <85 class _ElementType,86 class _Extents,87 class _LayoutPolicy = layout_right,88 class _AccessorPolicy = default_accessor<_ElementType>89>90class mdspan91{92private:93 static_assert(__detail::__is_extents_v<_Extents>, "mdspan's Extents template parameter must be a specialization of _CUDA_VSTD::extents.");94 95 // Workaround for non-deducibility of the index sequence template parameter if it's given at the top level96 template <class>97 struct __deduction_workaround;98 99 template <size_t... _Idxs>100 struct __deduction_workaround<_CUDA_VSTD::index_sequence<_Idxs...>>101 {102 __MDSPAN_FORCE_INLINE_FUNCTION static constexpr103 size_t __size(mdspan const& __self) noexcept {104 return __MDSPAN_FOLD_TIMES_RIGHT((__self.__mapping_ref().extents().template __extent<_Idxs>()), /* * ... * */ size_t(1));105 }106 __MDSPAN_FORCE_INLINE_FUNCTION static constexpr107 bool __empty(mdspan const& __self) noexcept {108 return (__self.rank()>0) && __MDSPAN_FOLD_OR((__self.__mapping_ref().extents().template __extent<_Idxs>()==index_type(0)));109 }110 template <class _ReferenceType, class _SizeType, size_t _Np>111 __MDSPAN_FORCE_INLINE_FUNCTION static constexpr112 _ReferenceType __callop(mdspan const& __self, const _CUDA_VSTD::array<_SizeType, _Np>& __indices) noexcept {113 return __self.__accessor_ref().access(__self.__ptr_ref(), __self.__mapping_ref()(__indices[_Idxs]...));114 }115 template <class _ReferenceType, class _SizeType, size_t _Np>116 __MDSPAN_FORCE_INLINE_FUNCTION static constexpr117 _ReferenceType __callop(mdspan const& __self, const _CUDA_VSTD::span<_SizeType, _Np>& __indices) noexcept {118 return __self.__accessor_ref().access(__self.__ptr_ref(), __self.__mapping_ref()(__indices[_Idxs]...));119 }120 };121 122public:123 124 //--------------------------------------------------------------------------------125 // Domain and codomain types126 127 using extents_type = _Extents;128 using layout_type = _LayoutPolicy;129 using accessor_type = _AccessorPolicy;130 using mapping_type = typename layout_type::template mapping<extents_type>;131 using element_type = _ElementType;132 using value_type = _CUDA_VSTD::remove_cv_t<element_type>;133 using index_type = typename extents_type::index_type;134 using size_type = typename extents_type::size_type;135 using rank_type = typename extents_type::rank_type;136 using data_handle_type = typename accessor_type::data_handle_type;137 using reference = typename accessor_type::reference;138 139 __MDSPAN_INLINE_FUNCTION static constexpr size_t rank() noexcept { return extents_type::rank(); }140 __MDSPAN_INLINE_FUNCTION static constexpr size_t rank_dynamic() noexcept { return extents_type::rank_dynamic(); }141 __MDSPAN_INLINE_FUNCTION static constexpr size_t static_extent(size_t __r) noexcept { return extents_type::static_extent(__r); }142 __MDSPAN_INLINE_FUNCTION constexpr index_type extent(size_t __r) const noexcept { return __mapping_ref().extents().extent(__r); };143 144private:145 146 // Can't use defaulted parameter in the __deduction_workaround template because of a bug in MSVC warning C4348.147 using __impl = __deduction_workaround<_CUDA_VSTD::make_index_sequence<extents_type::rank()>>;148 149 using __map_acc_pair_t = __detail::__compressed_pair<mapping_type, accessor_type>;150 151public:152 153 //--------------------------------------------------------------------------------154 // [mdspan.basic.cons], mdspan constructors, assignment, and destructor155 156#if !__MDSPAN_HAS_CXX_20157 __MDSPAN_INLINE_FUNCTION_DEFAULTED constexpr mdspan() = default;158#else159 __MDSPAN_INLINE_FUNCTION_DEFAULTED constexpr mdspan()160 requires(161 // Directly using rank_dynamic()>0 here doesn't work for nvcc162 (extents_type::rank_dynamic() >0) &&163 _LIBCUDACXX_TRAIT(_CUDA_VSTD::is_default_constructible, data_handle_type) &&164 _LIBCUDACXX_TRAIT(_CUDA_VSTD::is_default_constructible, mapping_type) &&165 _LIBCUDACXX_TRAIT(_CUDA_VSTD::is_default_constructible, accessor_type)166 ) = default;167#endif168 __MDSPAN_INLINE_FUNCTION_DEFAULTED constexpr mdspan(const mdspan&) = default;169 __MDSPAN_INLINE_FUNCTION_DEFAULTED constexpr mdspan(mdspan&&) = default;170 171 __MDSPAN_TEMPLATE_REQUIRES(172 class... _SizeTypes,173 /* requires */ (174 __MDSPAN_FOLD_AND(_LIBCUDACXX_TRAIT(_CUDA_VSTD::is_convertible, _SizeTypes, index_type) /* && ... */) &&175 __MDSPAN_FOLD_AND(_LIBCUDACXX_TRAIT(_CUDA_VSTD::is_nothrow_constructible, index_type, _SizeTypes) /* && ... */) &&176 ((sizeof...(_SizeTypes) == rank()) || (sizeof...(_SizeTypes) == rank_dynamic())) &&177 _LIBCUDACXX_TRAIT(_CUDA_VSTD::is_constructible, mapping_type, extents_type) &&178 _LIBCUDACXX_TRAIT(_CUDA_VSTD::is_default_constructible, accessor_type)179 )180 )181 __MDSPAN_INLINE_FUNCTION182 explicit constexpr mdspan(data_handle_type __p, _SizeTypes... __dynamic_extents)183 // TODO @proposal-bug shouldn't I be allowed to do `move(__p)` here?184 : __members(_CUDA_VSTD::move(__p), __map_acc_pair_t(mapping_type(extents_type(static_cast<index_type>(_CUDA_VSTD::move(__dynamic_extents))...)), accessor_type()))185 { }186 187 __MDSPAN_TEMPLATE_REQUIRES(188 class _SizeType, size_t _Np,189 /* requires */ (190 _LIBCUDACXX_TRAIT(_CUDA_VSTD::is_convertible, _SizeType, index_type) &&191 _LIBCUDACXX_TRAIT(_CUDA_VSTD::is_nothrow_constructible, index_type, _SizeType) &&192 ((_Np == rank()) || (_Np == rank_dynamic())) &&193 _LIBCUDACXX_TRAIT(_CUDA_VSTD::is_constructible, mapping_type, extents_type) &&194 _LIBCUDACXX_TRAIT(_CUDA_VSTD::is_default_constructible, accessor_type)195 )196 )197 __MDSPAN_CONDITIONAL_EXPLICIT(_Np != rank_dynamic())198 __MDSPAN_INLINE_FUNCTION199 constexpr mdspan(data_handle_type __p, const _CUDA_VSTD::array<_SizeType, _Np>& __dynamic_extents)200 : __members(_CUDA_VSTD::move(__p), __map_acc_pair_t(mapping_type(extents_type(__dynamic_extents)), accessor_type()))201 { }202 203 __MDSPAN_TEMPLATE_REQUIRES(204 class _SizeType, size_t _Np,205 /* requires */ (206 _LIBCUDACXX_TRAIT(_CUDA_VSTD::is_convertible, _SizeType, index_type) &&207 _LIBCUDACXX_TRAIT(_CUDA_VSTD::is_nothrow_constructible, index_type, _SizeType) &&208 ((_Np == rank()) || (_Np == rank_dynamic())) &&209 _LIBCUDACXX_TRAIT(_CUDA_VSTD::is_constructible, mapping_type, extents_type) &&210 _LIBCUDACXX_TRAIT(_CUDA_VSTD::is_default_constructible, accessor_type)211 )212 )213 __MDSPAN_CONDITIONAL_EXPLICIT(_Np != rank_dynamic())214 __MDSPAN_INLINE_FUNCTION215 constexpr mdspan(data_handle_type __p, _CUDA_VSTD::span<_SizeType, _Np> __dynamic_extents)216 : __members(_CUDA_VSTD::move(__p), __map_acc_pair_t(mapping_type(extents_type(_CUDA_VSTD::as_const(__dynamic_extents))), accessor_type()))217 { }218 219 __MDSPAN_FUNCTION_REQUIRES(220 (__MDSPAN_INLINE_FUNCTION constexpr),221 mdspan, (data_handle_type __p, const extents_type& __exts), ,222 /* requires */ (_LIBCUDACXX_TRAIT(_CUDA_VSTD::is_default_constructible, accessor_type) &&223 _LIBCUDACXX_TRAIT(_CUDA_VSTD::is_constructible, mapping_type, extents_type))224 ) : __members(_CUDA_VSTD::move(__p), __map_acc_pair_t(mapping_type(__exts), accessor_type()))225 { }226 227 __MDSPAN_FUNCTION_REQUIRES(228 (__MDSPAN_INLINE_FUNCTION constexpr),229 mdspan, (data_handle_type __p, const mapping_type& __m), ,230 /* requires */ (_LIBCUDACXX_TRAIT(_CUDA_VSTD::is_default_constructible, accessor_type))231 ) : __members(_CUDA_VSTD::move(__p), __map_acc_pair_t(__m, accessor_type()))232 { }233 234 __MDSPAN_INLINE_FUNCTION235 constexpr mdspan(data_handle_type __p, const mapping_type& __m, const accessor_type& __a)236 : __members(_CUDA_VSTD::move(__p), __map_acc_pair_t(__m, __a))237 { }238 239 __MDSPAN_TEMPLATE_REQUIRES(240 class _OtherElementType, class _OtherExtents, class _OtherLayoutPolicy, class _OtherAccessor,241 /* requires */ (242 _LIBCUDACXX_TRAIT(_CUDA_VSTD::is_constructible, mapping_type, typename _OtherLayoutPolicy::template mapping<_OtherExtents>) &&243 _LIBCUDACXX_TRAIT(_CUDA_VSTD::is_constructible, accessor_type, _OtherAccessor)244 )245 )246 __MDSPAN_INLINE_FUNCTION247 constexpr mdspan(const mdspan<_OtherElementType, _OtherExtents, _OtherLayoutPolicy, _OtherAccessor>& __other)248 : __members(__other.__ptr_ref(), __map_acc_pair_t(__other.__mapping_ref(), __other.__accessor_ref()))249 {250 static_assert(_LIBCUDACXX_TRAIT(_CUDA_VSTD::is_constructible, data_handle_type, typename _OtherAccessor::data_handle_type),"Incompatible data_handle_type for mdspan construction");251 static_assert(_LIBCUDACXX_TRAIT(_CUDA_VSTD::is_constructible, extents_type, _OtherExtents),"Incompatible extents for mdspan construction");252 /*253 * TODO: Check precondition254 * For each rank index __r of extents_type, static_extent(__r) == dynamic_extent || static_extent(__r) == __other.extent(__r) is true.255 */256 }257 258 /* Might need this on NVIDIA?259 __MDSPAN_INLINE_FUNCTION_DEFAULTED260 ~mdspan() = default;261 */262 263 __MDSPAN_INLINE_FUNCTION_DEFAULTED __MDSPAN_CONSTEXPR_14_DEFAULTED mdspan& operator=(const mdspan&) = default;264 __MDSPAN_INLINE_FUNCTION_DEFAULTED __MDSPAN_CONSTEXPR_14_DEFAULTED mdspan& operator=(mdspan&&) = default;265 266 267 //--------------------------------------------------------------------------------268 // [mdspan.basic.mapping], mdspan mapping domain multidimensional index to access codomain element269 270 #if __MDSPAN_USE_BRACKET_OPERATOR271 __MDSPAN_TEMPLATE_REQUIRES(272 class... _SizeTypes,273 /* requires */ (274 __MDSPAN_FOLD_AND(_LIBCUDACXX_TRAIT(_CUDA_VSTD::is_convertible, _SizeTypes, index_type) /* && ... */) &&275 __MDSPAN_FOLD_AND(_LIBCUDACXX_TRAIT(_CUDA_VSTD::is_nothrow_constructible, index_type, _SizeTypes) /* && ... */) &&276 (rank() == sizeof...(_SizeTypes))277 )278 )279 __MDSPAN_FORCE_INLINE_FUNCTION280 constexpr reference operator[](_SizeTypes... __indices) const281 {282 return __accessor_ref().access(__ptr_ref(), __mapping_ref()(index_type(__indices)...));283 }284 #endif285 286 __MDSPAN_TEMPLATE_REQUIRES(287 class _SizeType,288 /* requires */ (289 _LIBCUDACXX_TRAIT(_CUDA_VSTD::is_convertible, _SizeType, index_type) &&290 _LIBCUDACXX_TRAIT(_CUDA_VSTD::is_nothrow_constructible, index_type, _SizeType)291 )292 )293 __MDSPAN_FORCE_INLINE_FUNCTION294 constexpr reference operator[](const _CUDA_VSTD::array<_SizeType, rank()>& __indices) const295 {296 return __impl::template __callop<reference>(*this, __indices);297 }298 299 __MDSPAN_TEMPLATE_REQUIRES(300 class _SizeType,301 /* requires */ (302 _LIBCUDACXX_TRAIT(_CUDA_VSTD::is_convertible, _SizeType, index_type) &&303 _LIBCUDACXX_TRAIT(_CUDA_VSTD::is_nothrow_constructible, index_type, _SizeType)304 )305 )306 __MDSPAN_FORCE_INLINE_FUNCTION307 constexpr reference operator[](_CUDA_VSTD::span<_SizeType, rank()> __indices) const308 {309 return __impl::template __callop<reference>(*this, __indices);310 }311 312 #if !__MDSPAN_USE_BRACKET_OPERATOR313 __MDSPAN_TEMPLATE_REQUIRES(314 class _Index,315 /* requires */ (316 _LIBCUDACXX_TRAIT(_CUDA_VSTD::is_convertible, _Index, index_type) &&317 _LIBCUDACXX_TRAIT(_CUDA_VSTD::is_nothrow_constructible, index_type, _Index) &&318 extents_type::rank() == 1319 )320 )321 __MDSPAN_FORCE_INLINE_FUNCTION322 constexpr reference operator[](_Index __idx) const323 {324 return __accessor_ref().access(__ptr_ref(), __mapping_ref()(index_type(__idx)));325 }326 #endif327 328 #if __MDSPAN_USE_PAREN_OPERATOR329 __MDSPAN_TEMPLATE_REQUIRES(330 class... _SizeTypes,331 /* requires */ (332 __MDSPAN_FOLD_AND(_LIBCUDACXX_TRAIT(_CUDA_VSTD::is_convertible, _SizeTypes, index_type) /* && ... */) &&333 __MDSPAN_FOLD_AND(_LIBCUDACXX_TRAIT(_CUDA_VSTD::is_nothrow_constructible, index_type, _SizeTypes) /* && ... */) &&334 extents_type::rank() == sizeof...(_SizeTypes)335 )336 )337 __MDSPAN_FORCE_INLINE_FUNCTION338 constexpr reference operator()(_SizeTypes... __indices) const339 {340 return __accessor_ref().access(__ptr_ref(), __mapping_ref()(__indices...));341 }342 343 __MDSPAN_TEMPLATE_REQUIRES(344 class _SizeType,345 /* requires */ (346 _LIBCUDACXX_TRAIT(_CUDA_VSTD::is_convertible, _SizeType, index_type) &&347 _LIBCUDACXX_TRAIT(_CUDA_VSTD::is_nothrow_constructible, index_type, _SizeType)348 )349 )350 __MDSPAN_FORCE_INLINE_FUNCTION351 constexpr reference operator()(const _CUDA_VSTD::array<_SizeType, rank()>& __indices) const352 {353 return __impl::template __callop<reference>(*this, __indices);354 }355 356 __MDSPAN_TEMPLATE_REQUIRES(357 class _SizeType,358 /* requires */ (359 _LIBCUDACXX_TRAIT(_CUDA_VSTD::is_convertible, _SizeType, index_type) &&360 _LIBCUDACXX_TRAIT(_CUDA_VSTD::is_nothrow_constructible, index_type, _SizeType)361 )362 )363 __MDSPAN_FORCE_INLINE_FUNCTION364 constexpr reference operator()(_CUDA_VSTD::span<_SizeType, rank()> __indices) const365 {366 return __impl::template __callop<reference>(*this, __indices);367 }368 #endif // __MDSPAN_USE_PAREN_OPERATOR369 370 __MDSPAN_INLINE_FUNCTION constexpr size_t size() const noexcept {371 return __impl::__size(*this);372 };373 374 __MDSPAN_INLINE_FUNCTION constexpr bool empty() const noexcept {375 return __impl::__empty(*this);376 };377 378 __MDSPAN_INLINE_FUNCTION379 friend constexpr void swap(mdspan& __x, mdspan& __y) noexcept {380 swap(__x.__ptr_ref(), __y.__ptr_ref());381 swap(__x.__mapping_ref(), __y.__mapping_ref());382 swap(__x.__accessor_ref(), __y.__accessor_ref());383 }384 385 //--------------------------------------------------------------------------------386 // [mdspan.basic.domobs], mdspan observers of the domain multidimensional index space387 388 389 __MDSPAN_INLINE_FUNCTION constexpr const extents_type& extents() const noexcept { return __mapping_ref().extents(); };390 __MDSPAN_INLINE_FUNCTION constexpr const data_handle_type& data_handle() const noexcept { return __ptr_ref(); };391 __MDSPAN_INLINE_FUNCTION constexpr const mapping_type& mapping() const noexcept { return __mapping_ref(); };392 __MDSPAN_INLINE_FUNCTION constexpr const accessor_type& accessor() const noexcept { return __accessor_ref(); };393 394 //--------------------------------------------------------------------------------395 // [mdspan.basic.obs], mdspan observers of the mapping396 397 __MDSPAN_INLINE_FUNCTION static constexpr bool is_always_unique() noexcept { return mapping_type::is_always_unique(); };398 __MDSPAN_INLINE_FUNCTION static constexpr bool is_always_exhaustive() noexcept { return mapping_type::is_always_exhaustive(); };399 __MDSPAN_INLINE_FUNCTION static constexpr bool is_always_strided() noexcept { return mapping_type::is_always_strided(); };400 401 __MDSPAN_INLINE_FUNCTION constexpr bool is_unique() const noexcept { return __mapping_ref().is_unique(); };402 __MDSPAN_INLINE_FUNCTION constexpr bool is_exhaustive() const noexcept { return __mapping_ref().is_exhaustive(); };403 __MDSPAN_INLINE_FUNCTION constexpr bool is_strided() const noexcept { return __mapping_ref().is_strided(); };404 __MDSPAN_INLINE_FUNCTION constexpr index_type stride(size_t __r) const { return __mapping_ref().stride(__r); };405 406private:407 408 __detail::__compressed_pair<data_handle_type, __map_acc_pair_t> __members{};409 410 __MDSPAN_FORCE_INLINE_FUNCTION constexpr data_handle_type& __ptr_ref() noexcept { return __members.__first(); }411 __MDSPAN_FORCE_INLINE_FUNCTION constexpr data_handle_type const& __ptr_ref() const noexcept { return __members.__first(); }412 __MDSPAN_FORCE_INLINE_FUNCTION constexpr mapping_type& __mapping_ref() noexcept { return __members.__second().__first(); }413 __MDSPAN_FORCE_INLINE_FUNCTION constexpr mapping_type const& __mapping_ref() const noexcept { return __members.__second().__first(); }414 __MDSPAN_FORCE_INLINE_FUNCTION constexpr accessor_type& __accessor_ref() noexcept { return __members.__second().__second(); }415 __MDSPAN_FORCE_INLINE_FUNCTION constexpr accessor_type const& __accessor_ref() const noexcept { return __members.__second().__second(); }416 417 template <class, class, class, class>418 friend class mdspan;419 420};421 422#if defined(__MDSPAN_USE_CLASS_TEMPLATE_ARGUMENT_DEDUCTION)423__MDSPAN_TEMPLATE_REQUIRES(424 class _ElementType, class... _SizeTypes,425 /* requires */ __MDSPAN_FOLD_AND(_LIBCUDACXX_TRAIT(is_integral, _SizeTypes) /* && ... */) &&426 (sizeof...(_SizeTypes) > 0)427)428_LIBCUDACXX_HOST_DEVICE explicit mdspan(_ElementType*, _SizeTypes...)429 -> mdspan<_ElementType, dextents<size_t, sizeof...(_SizeTypes)>>;430 431__MDSPAN_TEMPLATE_REQUIRES(432 class _Pointer,433 (_LIBCUDACXX_TRAIT(is_pointer, _CUDA_VSTD::remove_reference_t<_Pointer>))434)435_LIBCUDACXX_HOST_DEVICE mdspan(_Pointer&&) -> mdspan<_CUDA_VSTD::remove_pointer_t<_CUDA_VSTD::remove_reference_t<_Pointer>>, extents<size_t>>;436__MDSPAN_TEMPLATE_REQUIRES(437 class _CArray,438 (_LIBCUDACXX_TRAIT(is_array, _CArray) && (rank_v<_CArray> == 1))439)440_LIBCUDACXX_HOST_DEVICE mdspan(_CArray&) -> mdspan<_CUDA_VSTD::remove_all_extents_t<_CArray>, extents<size_t, _CUDA_VSTD::extent_v<_CArray,0>>>;441 442template <class _ElementType, class _SizeType, size_t _Np>443_LIBCUDACXX_HOST_DEVICE mdspan(_ElementType*, const _CUDA_VSTD::array<_SizeType, _Np>&)444 -> mdspan<_ElementType, dextents<size_t, _Np>>;445 446template <class _ElementType, class _SizeType, size_t _Np>447_LIBCUDACXX_HOST_DEVICE mdspan(_ElementType*, _CUDA_VSTD::span<_SizeType, _Np>)448 -> mdspan<_ElementType, dextents<size_t, _Np>>;449 450// This one is necessary because all the constructors take `data_handle_type`s, not451// `_ElementType*`s, and `data_handle_type` is taken from `accessor_type::data_handle_type`, which452// seems to throw off automatic deduction guides.453template <class _ElementType, class _SizeType, size_t... _ExtentsPack>454_LIBCUDACXX_HOST_DEVICE mdspan(_ElementType*, const extents<_SizeType, _ExtentsPack...>&)455 -> mdspan<_ElementType, extents<_SizeType, _ExtentsPack...>>;456 457template <class _ElementType, class _MappingType>458_LIBCUDACXX_HOST_DEVICE mdspan(_ElementType*, const _MappingType&)459 -> mdspan<_ElementType, typename _MappingType::extents_type, typename _MappingType::layout_type>;460 461template <class _MappingType, class _AccessorType>462_LIBCUDACXX_HOST_DEVICE mdspan(const typename _AccessorType::data_handle_type, const _MappingType&, const _AccessorType&)463 -> mdspan<typename _AccessorType::element_type, typename _MappingType::extents_type, typename _MappingType::layout_type, _AccessorType>;464#endif465 466#endif // _LIBCUDACXX_STD_VER > 11467 468_LIBCUDACXX_END_NAMESPACE_STD469 470#endif // _LIBCUDACXX___MDSPAN_MDSPAN_HPP471 