Asylo
extent.h
Go to the documentation of this file.
1 /*
2  *
3  * Copyright 2018 Asylo authors
4  *
5  * Licensed under the Apache License, Version 2.0 (the "License");
6  * you may not use this file except in compliance with the License.
7  * You may obtain a copy of the License at
8  *
9  * http://www.apache.org/licenses/LICENSE-2.0
10  *
11  * Unless required by applicable law or agreed to in writing, software
12  * distributed under the License is distributed on an "AS IS" BASIS,
13  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14  * See the License for the specific language governing permissions and
15  * limitations under the License.
16  *
17  */
18 
19 #ifndef ASYLO_PLATFORM_PRIMITIVES_EXTENT_H_
20 #define ASYLO_PLATFORM_PRIMITIVES_EXTENT_H_
21 
22 #include <cstddef>
23 #include <cstdint>
24 #include <cstring>
25 #include <functional>
26 #include <type_traits>
27 
28 namespace asylo {
29 namespace primitives {
30 
31 /// \class Extent extent.h asylo/platform/primitives/extent.h
32 /// A extent object suitable for sharing address ranges between trusted and
33 /// untrusted code.
34 class Extent {
35  public:
36  /// Initializes an empty extent.
37  constexpr Extent() : Extent(/*data=*/nullptr, /*size=*/0) {}
38 
39  /// Initializes an extent with a void pointer.
40  ///
41  /// \param data A pointer to the start of the extent of memory.
42  /// \param size The number of bytes in the extent.
43  constexpr Extent(void *data, size_t size)
44  : data_(data), size_(size) {}
45 
46  /// Initializes an extent with a pointer to a value.
47  ///
48  /// The number of bytes stored for the extent is sizeof(T).
49  ///
50  /// \param data A pointer to an object of type T
51  template <typename T>
52  explicit constexpr Extent(T *data)
53  : data_(raw_pointer(data)), size_(sizeof(T)) {}
54 
55  /// Initializes an extent with a pointer to an array of `count` objects of
56  /// type T.
57  ///
58  /// The size of the extent is `count * sizeof(T)`.
59  ///
60  /// \param data A pointer to the start of the array slice.
61  /// \param count The number of elements included in the extent.
62  template <typename T>
63  constexpr Extent(T *data, size_t count)
64  : data_(raw_pointer(data)), size_(count * sizeof(T)) {}
65 
66  /// \returns The size of the extent in bytes.
67  size_t size() const { return size_; }
68 
69  /// \returns The extent data as a pointer to an array of bytes.
70  void *data() { return data_; }
71 
72  /// \returns The extent data as a constant pointer to an array of bytes.
73  const void *data() const { return data_; }
74 
75  /// A predicate for whether the extent is empty.
76  /// \returns True if and only if either the extent data is null or the size
77  /// is 0.
78  bool empty() const { return data_ == nullptr || size_ == 0; }
79 
80  /// Copies the contents of the extent to `out`. The caller is responsible for
81  /// allocating and freeing `out` correctly.
82  ///
83  /// \param out A pointer to a mutable array of bytes.
84  void CopyTo(char *out) const {
85  memcpy(out, data_, size_);
86  }
87 
88  /// A size-aware reinterpret_cast for a mutable pointer.
89  ///
90  /// \returns The extent data as a pointer to an object of type T, or nullptr
91  /// if the extent is smaller than sizeof(T).
92  template <typename T>
93  T *As() {
94  return size_ >= sizeof(T) ? reinterpret_cast<T *>(data_) : nullptr;
95  }
96 
97  /// A size-aware reinterpret_cast for a constant pointer.
98  ///
99  /// \returns The extent data as a constant pointer to an object of type T, or
100  /// nullptr if the extent is smaller than sizeof(T).
101  template <typename T>
102  const T *As() const {
103  return size_ >= sizeof(T) ? reinterpret_cast<const T *>(data_) : nullptr;
104  }
105 
106  private:
107  template <typename T>
108  static constexpr void *raw_pointer(const T *ptr) {
109  return reinterpret_cast<void *>(const_cast<T *>(ptr));
110  }
111 
112  template <typename T>
113  static constexpr void *raw_pointer(T *ptr) {
114  return reinterpret_cast<void *>(ptr);
115  }
116 
117  // This method is not intended to be called, it is defined only to provide a
118  // scope where offsetof may be applied to private members and Extent is
119  // a complete type.
120  static void CheckLayout() {
121  static_assert(std::is_trivially_copy_assignable<Extent>::value,
122  "Extent must satisfy std::is_trivially_copy_assignable");
123  static_assert(std::is_standard_layout<Extent>::value,
124  "Extent must satisfy std::is_standard_layout");
125  static_assert(sizeof(size_t) == 8, "Unexpected size for type size_t");
126  static_assert(offsetof(Extent, data_) == 0x0,
127  "Unexpected layout for field Extent::data_");
128  static_assert(offsetof(Extent, size_) == sizeof(uint64_t),
129  "Unexpected layout for field Extent::size_");
130  }
131 
132  void *data_;
133  size_t size_;
134 };
135 
136 /// The callback signature for a function which performs custom allocation of
137 /// an Extent.
139 
140 } // namespace primitives
141 } // namespace asylo
142 
143 #endif // ASYLO_PLATFORM_PRIMITIVES_EXTENT_H_
size_t size() const
Definition: extent.h:67
constexpr Extent(T *data)
Initializes an extent with a pointer to a value.
Definition: extent.h:52
T * As()
A size-aware reinterpret_cast for a mutable pointer.
Definition: extent.h:93
void CopyTo(char *out) const
Copies the contents of the extent to out.
Definition: extent.h:84
ABSL_CONST_INIT const char kStatusMoveAssignmentMsg[]
const T * As() const
A size-aware reinterpret_cast for a constant pointer.
Definition: extent.h:102
constexpr Extent()
Initializes an empty extent.
Definition: extent.h:37
constexpr Extent(T *data, size_t count)
Initializes an extent with a pointer to an array of count objects of type T.
Definition: extent.h:63
const void * data() const
Definition: extent.h:73
constexpr Extent(void *data, size_t size)
Initializes an extent with a void pointer.
Definition: extent.h:43
void * data()
Definition: extent.h:70
A extent object suitable for sharing address ranges between trusted and untrusted code...
Definition: extent.h:34
Definition: extent.h:29
bool empty() const
A predicate for whether the extent is empty.
Definition: extent.h:78