8#ifndef BOTAN_TLS_SEQ_NUMBERS_H_
9#define BOTAN_TLS_SEQ_NUMBERS_H_
11#include <botan/assert.h>
12#include <botan/exceptn.h>
63 if(m_write_seq_no == std::numeric_limits<uint64_t>::max()) {
64 throw Invalid_State(
"TLS 1.2 write sequence number overflow");
66 return m_write_seq_no++;
74 if(m_read_seq_no == std::numeric_limits<uint64_t>::max()) {
81 uint64_t m_write_seq_no;
82 uint64_t m_read_seq_no;
83 uint16_t m_read_epoch;
84 uint16_t m_write_epoch;
96 m_read_windows.clear();
97 m_read_windows[0] = Replay_Window{};
101 m_read_epoch = next_epoch(m_read_epoch);
102 m_read_windows.try_emplace(m_read_epoch);
103 prune_epochs(m_read_windows, m_read_epoch);
107 m_write_epoch = next_epoch(m_write_epoch);
108 m_write_seqs[m_write_epoch] = 0;
109 prune_epochs(m_write_seqs, m_write_epoch);
117 auto i = m_write_seqs.find(epoch);
118 if(i == m_write_seqs.end()) {
121 if(i->second > 0x0000FFFFFFFFFFFF) {
124 return (
static_cast<uint64_t
>(epoch) << 48) | i->second++;
130 const uint16_t epoch =
static_cast<uint16_t
>(sequence >> 48);
131 const uint64_t record_sequence = sequence & 0x0000FFFFFFFFFFFF;
132 const auto window = m_read_windows.find(epoch);
134 if(window == m_read_windows.end()) {
138 const size_t window_size =
sizeof(window->second.bits) * 8;
140 if(record_sequence > window->second.highest) {
144 const uint64_t offset = window->second.highest - record_sequence;
146 if(offset >= window_size) {
150 return (((window->second.bits >> offset) & 1) == 1);
154 const uint16_t epoch =
static_cast<uint16_t
>(sequence >> 48);
155 const uint64_t record_sequence = sequence & 0x0000FFFFFFFFFFFF;
156 auto& window = m_read_windows[epoch];
157 const size_t window_size =
sizeof(window.bits) * 8;
159 if(record_sequence > window.highest) {
161 const uint64_t offset = record_sequence - window.highest;
162 window.highest += offset;
164 if(offset >= window_size) {
167 window.bits <<= offset;
172 const uint64_t offset = window.highest - record_sequence;
174 if(offset < window_size) {
176 window.bits |= (
static_cast<uint64_t
>(1) << offset);
181 window.highest = record_sequence;
188 struct Replay_Window final {
189 uint64_t highest = 0;
201 static uint16_t next_epoch(uint16_t epoch) {
202 if(epoch == std::numeric_limits<uint16_t>::max()) {
205 return static_cast<uint16_t
>(epoch + 1);
217 template <
typename T>
218 static void prune_epochs(std::map<uint16_t, T>& epochs, uint16_t current) {
219 for(
auto i = epochs.begin(); i != epochs.end();) {
220 if(i->first == 0 || i->first + 1 >= current) {
228 std::map<uint16_t, uint64_t> m_write_seqs;
229 std::map<uint16_t, Replay_Window> m_read_windows;
230 uint16_t m_write_epoch = 0;
231 uint16_t m_read_epoch = 0;
virtual uint16_t current_read_epoch() const =0
virtual uint64_t next_read_sequence()=0
virtual ~Connection_Sequence_Numbers()=default
virtual void read_accept(uint64_t seq)=0
virtual uint16_t current_write_epoch() const =0
virtual void new_read_cipher_state()=0
virtual bool already_seen(uint64_t seq) const =0
virtual void new_write_cipher_state()=0
virtual uint64_t next_write_sequence(uint16_t)=0
uint64_t next_read_sequence() override
void read_accept(uint64_t sequence) override
uint16_t current_read_epoch() const override
void new_read_cipher_state() override
uint16_t current_write_epoch() const override
uint64_t next_write_sequence(uint16_t epoch) override
bool already_seen(uint64_t sequence) const override
void new_write_cipher_state() override
Datagram_Sequence_Numbers()
uint64_t next_write_sequence(uint16_t) override
uint64_t next_read_sequence() override
void read_accept(uint64_t) override
Stream_Sequence_Numbers()
void new_read_cipher_state() override
void new_write_cipher_state() override
uint16_t current_read_epoch() const override
bool already_seen(uint64_t) const override
uint16_t current_write_epoch() const override