Low-Level Abstraction of Memory Access
Byteswap.hpp
Go to the documentation of this file.
1 // Copyright 2022 Bernhard Manfred Gruber
2 // SPDX-License-Identifier: MPL-2.0
3 
4 #pragma once
5 
6 #include "../Core.hpp"
7 #include "../ProxyRefOpMixin.hpp"
8 #include "Common.hpp"
9 #include "Projection.hpp"
10 
11 namespace llama::mapping
12 {
13  namespace internal
14  {
15  // TODO(bgruber): replace by std::byteswap in C++23
16  template<typename T>
18  {
19  if constexpr(sizeof(T) == 1)
20  return t;
21  else
22  {
23  llama::Array<std::byte, sizeof(T)> arr{};
24  std::memcpy(&arr, &t, sizeof(T));
25 
26  for(std::size_t i = 0; i < sizeof(T) / 2; i++)
27  {
28  const auto a = arr[i];
29  const auto b = arr[sizeof(T) - 1 - i];
30  arr[i] = b;
31  arr[sizeof(T) - 1 - i] = a;
32  }
33 
34  std::memcpy(&t, &arr, sizeof(T));
35  return t;
36  }
37  }
38 
39  template<typename T>
41  {
42  LLAMA_FN_HOST_ACC_INLINE static auto load(T v) -> T
43  {
44  return byteswap(v);
45  }
46 
47  LLAMA_FN_HOST_ACC_INLINE static auto store(T v) -> T
48  {
49  return byteswap(v);
50  }
51  };
52 
53  template<typename T>
54  using MakeByteswapProjectionPair = mp_list<T, ByteswapProjection<T>>;
55 
56  template<typename RecordDim>
58  = mp_transform<MakeByteswapProjectionPair, mp_unique<FlatRecordDim<RecordDim>>>;
59  } // namespace internal
60 
63  template<typename ArrayExtents, typename RecordDim, template<typename, typename> typename InnerMapping>
64  struct Byteswap : Projection<ArrayExtents, RecordDim, InnerMapping, internal::MakeByteswapProjectionMap<RecordDim>>
65  {
66  private:
68 
69  public:
70  using Base::Base;
71  };
72 
76  template<template<typename, typename> typename InnerMapping>
77  struct BindByteswap
78  {
79  template<typename ArrayExtents, typename RecordDim>
81  };
82 
84  template<typename Mapping>
85  inline constexpr bool isByteswap = false;
86 
88  template<typename TArrayExtents, typename TRecordDim, template<typename, typename> typename InnerMapping>
89  inline constexpr bool isByteswap<Byteswap<TArrayExtents, TRecordDim, InnerMapping>> = true;
90 } // namespace llama::mapping
#define LLAMA_EXPORT
Definition: macros.hpp:192
#define LLAMA_FN_HOST_ACC_INLINE
Definition: macros.hpp:96
constexpr auto memcpy
Definition: Copy.hpp:32
mp_list< T, ByteswapProjection< T > > MakeByteswapProjectionPair
Definition: Byteswap.hpp:54
auto byteswap(T t) -> T
Definition: Byteswap.hpp:17
mp_transform< MakeByteswapProjectionPair, mp_unique< FlatRecordDim< RecordDim > >> MakeByteswapProjectionMap
Definition: Byteswap.hpp:58
constexpr bool isByteswap
Definition: Byteswap.hpp:85
Mapping that swaps the byte order of all values when loading/storing.
Definition: Byteswap.hpp:65