Nexus HTTP/3
A QUIC and HTTP/3 library
connection_id.hpp
1 #pragma once
2 
3 #include <algorithm>
4 #include <array>
5 #include <cstdint>
6 #include <iterator>
7 #include <stdexcept>
8 
9 namespace nexus::quic {
10 
13  public:
14  using value_type = unsigned char;
15  using size_type = std::uint_fast8_t;
16  using difference_type = std::ptrdiff_t;
17  using reference = value_type&;
18  using const_reference = const value_type&;
19  using pointer = value_type*;
20  using const_pointer = const value_type*;
21  using iterator = pointer;
22  using const_iterator = const_pointer;
23  using reverse_iterator = std::reverse_iterator<iterator>;
24  using const_reverse_iterator = std::reverse_iterator<const_iterator>;
25 
27  constexpr connection_id() noexcept
28  : data_{}, size_(0)
29  {}
31  template <size_t Size>
32  constexpr connection_id(const value_type (&data)[Size]) noexcept
33  : data_{}, size_(Size)
34  {
35  static_assert(Size <= max_size_);
36  for (size_type i = 0; i < Size; i++) {
37  data_[i] = data[i];
38  }
39  }
41  template <size_t Size>
42  constexpr connection_id(const std::array<value_type, Size>& data) noexcept
43  : data_{}, size_(Size)
44  {
45  static_assert(Size <= max_size_);
46  for (size_type i = 0; i < Size; i++) {
47  data_[i] = data[i];
48  }
49  }
52  constexpr connection_id(const_pointer data, size_type size)
53  : data_{}, size_(size)
54  {
55  if (size > max_size_) {
56  throw std::length_error("maximum connection id length (20) exceeded");
57  }
58  for (size_type i = 0; i < size; i++) {
59  data_[i] = data[i];
60  }
61  }
62 
64  constexpr connection_id(const connection_id&) noexcept = default;
66  constexpr connection_id& operator=(const connection_id&) noexcept = default;
67 
69  constexpr bool empty() const noexcept { return size_ == 0; }
71  constexpr size_type size() const { return size_; }
73  constexpr static size_type max_size() { return max_size_; }
74 
76  constexpr void resize(size_type size)
77  {
78  if (size > max_size_) {
79  throw std::length_error("maximum connection id length (20) exceeded");
80  }
81  size_ = size;
82  }
83 
86  constexpr reference at(size_type p)
87  {
88  if (p >= size()) {
89  throw std::out_of_range("array index out of range");
90  }
91  return data_[p];
92  }
94  constexpr const_reference at(size_type p) const
95  {
96  if (p >= size()) {
97  throw std::out_of_range("array index out of range");
98  }
99  return data_[p];
100  }
101 
104  constexpr reference operator[](size_type p) { return data_[p]; }
106  constexpr const_reference operator[](size_type p) const { return data_[p]; }
107 
109  constexpr reference front() { return data_.front(); }
111  constexpr const_reference front() const { return data_.front(); }
112 
114  constexpr reference back() { return *std::prev(end()); }
116  constexpr const_reference back() const { return *std::prev(end()); }
117 
119  constexpr pointer data() { return data_.data(); }
121  constexpr const_pointer data() const { return data_.data(); }
122 
124  constexpr iterator begin() { return data_.begin(); }
126  constexpr const_iterator begin() const { return data_.begin(); }
128  constexpr const_iterator cbegin() const { return data_.cbegin(); }
129 
131  constexpr iterator end() { return std::next(begin(), size_); }
133  constexpr const_iterator end() const { return std::next(begin(), size_); }
135  constexpr const_iterator cend() const { return std::next(begin(), size_); }
136 
138  constexpr reverse_iterator rbegin() {
139  return std::next(data_.rbegin(), max_size_ - size_);
140  }
142  constexpr const_reverse_iterator rbegin() const {
143  return std::next(data_.rbegin(), max_size_ - size_);
144  }
146  constexpr const_reverse_iterator crbegin() const {
147  return std::next(data_.rbegin(), max_size_ - size_);
148  }
149 
151  constexpr reverse_iterator rend() { return data_.rend(); }
153  constexpr const_reverse_iterator rend() const { return data_.rend(); }
155  constexpr const_reverse_iterator crend() const { return data_.crend(); }
156 
157  private:
158  static constexpr size_type max_size_ = 20;
159  using array_type = std::array<value_type, max_size_>;
160  array_type data_;
161  size_type size_;
162 };
163 
166 inline bool operator==(const connection_id& l, const connection_id& r) noexcept
167 {
168  return l.size() == r.size() && std::equal(l.begin(), l.end(), r.begin());
169 }
172 inline bool operator!=(const connection_id& l, const connection_id& r) noexcept
173 {
174  return l.size() != r.size() || !std::equal(l.begin(), l.end(), r.begin());
175 }
178 inline bool operator<(const connection_id& l, const connection_id& r) noexcept
179 {
180  return std::lexicographical_compare(l.begin(), l.end(), r.begin(), r.end());
181 }
184 inline bool operator>(const connection_id& l, const connection_id& r) noexcept
185 {
186  return std::lexicographical_compare(r.begin(), r.end(), l.begin(), l.end());
187 }
190 inline bool operator<=(const connection_id& l, const connection_id& r) noexcept
191 {
192  return !(l > r);
193 }
196 inline bool operator>=(const connection_id& l, const connection_id& r) noexcept
197 {
198  return !(l < r);
199 }
200 
203 inline void swap(connection_id& lhs, connection_id& rhs) noexcept
204 {
205  auto tmp = lhs;
206  lhs = std::move(rhs);
207  rhs = std::move(tmp);
208 }
209 
210 } // namespace nexus::quic
an opaque connection id string
Definition: connection_id.hpp:12
constexpr const_iterator end() const
This is an overloaded member function, provided for convenience. It differs from the above function o...
Definition: connection_id.hpp:133
constexpr connection_id() noexcept
default-construct an empty connection id
Definition: connection_id.hpp:27
constexpr const_reference front() const
This is an overloaded member function, provided for convenience. It differs from the above function o...
Definition: connection_id.hpp:111
constexpr const_reference at(size_type p) const
This is an overloaded member function, provided for convenience. It differs from the above function o...
Definition: connection_id.hpp:94
constexpr reference operator[](size_type p)
return a reference to the element at the given position without bounds checking
Definition: connection_id.hpp:104
constexpr size_type size() const
return the size
Definition: connection_id.hpp:71
constexpr reference back()
return a reference to the last element
Definition: connection_id.hpp:114
constexpr static size_type max_size()
return the maximum size
Definition: connection_id.hpp:73
constexpr iterator begin()
return an iterator to the beginning
Definition: connection_id.hpp:124
constexpr connection_id(const value_type(&data)[Size]) noexcept
construct with a copy of the given array
Definition: connection_id.hpp:32
constexpr const_reference back() const
This is an overloaded member function, provided for convenience. It differs from the above function o...
Definition: connection_id.hpp:116
constexpr connection_id(const std::array< value_type, Size > &data) noexcept
construct with a copy of the given array
Definition: connection_id.hpp:42
bool operator!=(const connection_id &l, const connection_id &r) noexcept
inequality comparison for connection_ids
Definition: connection_id.hpp:172
constexpr const_iterator cbegin() const
This is an overloaded member function, provided for convenience. It differs from the above function o...
Definition: connection_id.hpp:128
constexpr const_reverse_iterator crbegin() const
This is an overloaded member function, provided for convenience. It differs from the above function o...
Definition: connection_id.hpp:146
constexpr connection_id(const connection_id &) noexcept=default
construct with a copy of the given connection id
bool operator<(const connection_id &l, const connection_id &r) noexcept
less-than comparison for connection_ids
Definition: connection_id.hpp:178
bool operator==(const connection_id &l, const connection_id &r) noexcept
equality comparison for connection_ids
Definition: connection_id.hpp:166
constexpr connection_id(const_pointer data, size_type size)
construct with a copy of the given string. throws std::length_error if size exceeds max_size()
Definition: connection_id.hpp:52
constexpr reverse_iterator rbegin()
return a reverse iterator to the beginning
Definition: connection_id.hpp:138
constexpr reference front()
return a reference to the first element
Definition: connection_id.hpp:109
constexpr void resize(size_type size)
resize the connection id
Definition: connection_id.hpp:76
constexpr const_reverse_iterator crend() const
This is an overloaded member function, provided for convenience. It differs from the above function o...
Definition: connection_id.hpp:155
constexpr const_reverse_iterator rbegin() const
This is an overloaded member function, provided for convenience. It differs from the above function o...
Definition: connection_id.hpp:142
constexpr const_iterator cend() const
This is an overloaded member function, provided for convenience. It differs from the above function o...
Definition: connection_id.hpp:135
constexpr const_reverse_iterator rend() const
This is an overloaded member function, provided for convenience. It differs from the above function o...
Definition: connection_id.hpp:153
bool operator<=(const connection_id &l, const connection_id &r) noexcept
less-than-or-equal comparison for connection_ids
Definition: connection_id.hpp:190
constexpr const_pointer data() const
This is an overloaded member function, provided for convenience. It differs from the above function o...
Definition: connection_id.hpp:121
constexpr const_reference operator[](size_type p) const
This is an overloaded member function, provided for convenience. It differs from the above function o...
Definition: connection_id.hpp:106
constexpr iterator end()
return an iterator past the end
Definition: connection_id.hpp:131
constexpr reference at(size_type p)
return a reference to the element at the given position. throws std::out_of_range for invalid positio...
Definition: connection_id.hpp:86
constexpr connection_id & operator=(const connection_id &) noexcept=default
overwrite with a copy of the given connection id
constexpr pointer data()
return a pointer to the underlying bytes
Definition: connection_id.hpp:119
constexpr bool empty() const noexcept
return true if empty
Definition: connection_id.hpp:69
bool operator>=(const connection_id &l, const connection_id &r) noexcept
greater-than-or-equal comparison for connection_ids
Definition: connection_id.hpp:196
constexpr reverse_iterator rend()
return a reverse iterator to the endning
Definition: connection_id.hpp:151
constexpr const_iterator begin() const
This is an overloaded member function, provided for convenience. It differs from the above function o...
Definition: connection_id.hpp:126
void swap(connection_id &lhs, connection_id &rhs) noexcept
swap two connection_ids
Definition: connection_id.hpp:203
bool operator>(const connection_id &l, const connection_id &r) noexcept
greater-than comparison for connection_ids
Definition: connection_id.hpp:184
Generic QUIC library.
Definition: client.hpp:8