mirror of
https://github.com/llvm/llvm-project.git
synced 2025-04-27 16:56:06 +00:00

This commit implements layout_right in support of C++23 mdspan (https://wg21.link/p0009). layout_right is a layout mapping policy whose index mapping corresponds to the memory layout of multidimensional C-arrays, and is thus also referred to as the C-layout. Co-authored-by: Damien L-G <dalg24@gmail.com> Differential Revision: https://reviews.llvm.org/D151267
154 lines
5.3 KiB
Plaintext
154 lines
5.3 KiB
Plaintext
// -*-C++ - *-
|
|
//===----------------------------------------------------------------------===//
|
|
//
|
|
// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
|
|
// See https://llvm.org/LICENSE.txt for license information.
|
|
// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
|
|
//
|
|
//===---------------------------------------------------------------------===//
|
|
|
|
/*
|
|
|
|
// Overall mdspan synopsis
|
|
|
|
namespace std {
|
|
// [mdspan.extents], class template extents
|
|
template<class IndexType, size_t... Extents>
|
|
class extents;
|
|
|
|
// [mdspan.extents.dextents], alias template dextents
|
|
template<class IndexType, size_t Rank>
|
|
using dextents = see below;
|
|
|
|
// [mdspan.layout], layout mapping
|
|
struct layout_left; // not implemented yet
|
|
struct layout_right;
|
|
struct layout_stride; // not implemented yet
|
|
|
|
// [mdspan.accessor.default], class template default_accessor
|
|
template<class ElementType>
|
|
class default_accessor; // not implemented yet
|
|
|
|
// [mdspan.mdspan], class template mdspan
|
|
template<class ElementType, class Extents, class LayoutPolicy = layout_right,
|
|
class AccessorPolicy = default_accessor<ElementType>>
|
|
class mdspan; // not implemented yet
|
|
}
|
|
|
|
// extents synopsis
|
|
|
|
namespace std {
|
|
template<class _IndexType, size_t... _Extents>
|
|
class extents {
|
|
public:
|
|
using index_type = _IndexType;
|
|
using size_type = make_unsigned_t<index_type>;
|
|
using rank_type = size_t;
|
|
|
|
// [mdspan.extents.obs], observers of the multidimensional index space
|
|
static constexpr rank_type rank() noexcept { return sizeof...(_Extents); }
|
|
static constexpr rank_type rank_dynamic() noexcept { return dynamic-index(rank()); }
|
|
static constexpr size_t static_extent(rank_type) noexcept;
|
|
constexpr index_type extent(rank_type) const noexcept;
|
|
|
|
// [mdspan.extents.cons], constructors
|
|
constexpr extents() noexcept = default;
|
|
|
|
template<class _OtherIndexType, size_t... _OtherExtents>
|
|
constexpr explicit(see below)
|
|
extents(const extents<_OtherIndexType, _OtherExtents...>&) noexcept;
|
|
template<class... _OtherIndexTypes>
|
|
constexpr explicit extents(_OtherIndexTypes...) noexcept;
|
|
template<class _OtherIndexType, size_t N>
|
|
constexpr explicit(N != rank_dynamic())
|
|
extents(span<_OtherIndexType, N>) noexcept;
|
|
template<class _OtherIndexType, size_t N>
|
|
constexpr explicit(N != rank_dynamic())
|
|
extents(const array<_OtherIndexType, N>&) noexcept;
|
|
|
|
// [mdspan.extents.cmp], comparison operators
|
|
template<class _OtherIndexType, size_t... _OtherExtents>
|
|
friend constexpr bool operator==(const extents&,
|
|
const extents<_OtherIndexType, _OtherExtents...>&) noexcept;
|
|
|
|
private:
|
|
// libcxx note: we do not use an array here, but we need to preserve the as-if behavior
|
|
// for example the default constructor must zero initialize dynamic extents
|
|
array<index_type, rank_dynamic()> dynamic-extents{}; // exposition only
|
|
};
|
|
|
|
template<class... Integrals>
|
|
explicit extents(Integrals...)
|
|
-> see below;
|
|
}
|
|
|
|
// layout_right synopsis
|
|
|
|
namespace std {
|
|
template<class Extents>
|
|
class layout_right::mapping {
|
|
public:
|
|
using extents_type = Extents;
|
|
using index_type = typename extents_type::index_type;
|
|
using size_type = typename extents_type::size_type;
|
|
using rank_type = typename extents_type::rank_type;
|
|
using layout_type = layout_right;
|
|
|
|
// [mdspan.layout.right.cons], constructors
|
|
constexpr mapping() noexcept = default;
|
|
constexpr mapping(const mapping&) noexcept = default;
|
|
constexpr mapping(const extents_type&) noexcept;
|
|
template<class OtherExtents>
|
|
constexpr explicit(!is_convertible_v<OtherExtents, extents_type>)
|
|
mapping(const mapping<OtherExtents>&) noexcept;
|
|
template<class OtherExtents>
|
|
constexpr explicit(!is_convertible_v<OtherExtents, extents_type>)
|
|
mapping(const layout_left::mapping<OtherExtents>&) noexcept;
|
|
template<class OtherExtents>
|
|
constexpr explicit(extents_type::rank() > 0)
|
|
mapping(const layout_stride::mapping<OtherExtents>&) noexcept;
|
|
|
|
constexpr mapping& operator=(const mapping&) noexcept = default;
|
|
|
|
// [mdspan.layout.right.obs], observers
|
|
constexpr const extents_type& extents() const noexcept { return extents_; }
|
|
|
|
constexpr index_type required_span_size() const noexcept;
|
|
|
|
template<class... Indices>
|
|
constexpr index_type operator()(Indices...) const noexcept;
|
|
|
|
static constexpr bool is_always_unique() noexcept { return true; }
|
|
static constexpr bool is_always_exhaustive() noexcept { return true; }
|
|
static constexpr bool is_always_strided() noexcept { return true; }
|
|
|
|
static constexpr bool is_unique() noexcept { return true; }
|
|
static constexpr bool is_exhaustive() noexcept { return true; }
|
|
static constexpr bool is_strided() noexcept { return true; }
|
|
|
|
constexpr index_type stride(rank_type) const noexcept;
|
|
|
|
template<class OtherExtents>
|
|
friend constexpr bool operator==(const mapping&, const mapping<OtherExtents>&) noexcept;
|
|
|
|
private:
|
|
extents_type extents_{}; // exposition only
|
|
};
|
|
}
|
|
|
|
*/
|
|
|
|
#ifndef _LIBCPP_MDSPAN
|
|
#define _LIBCPP_MDSPAN
|
|
|
|
#include <__config>
|
|
#include <__fwd/mdspan.h>
|
|
#include <__mdspan/extents.h>
|
|
#include <__mdspan/layout_right.h>
|
|
|
|
#if !defined(_LIBCPP_HAS_NO_PRAGMA_SYSTEM_HEADER)
|
|
# pragma GCC system_header
|
|
#endif
|
|
|
|
#endif // _LIBCPP_MDSPAN
|