-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathblock.hpp
More file actions
70 lines (60 loc) · 2.48 KB
/
Copy pathblock.hpp
File metadata and controls
70 lines (60 loc) · 2.48 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
// Unless explicitly stated otherwise all files in this repository are licensed
// under the Apache License Version 2.0.
//
// This product includes software developed at Datadog (https://www.datadoghq.com/).
// Copyright 2025-Present Datadog, Inc.
#pragma once
#include <string_view>
namespace datadog::impl {
/**
* A block of data representing some payload generated by a feature.
*
* From the perspective of the Core, a Block is simply a contiguous span of bytes: the
* format of a given feature's blocks is an implementation detail of that feature. We
* use `std::string_view` in lieu of C++20's `std::span<uint8_t>`; but the Core should
* never peek at a block or assume that it represents textual data.
*
* Block is a lightweight, read-only wrapper that does not own the underlying data.
* Blocks must be copied to std::vector<uint8_t> for durable storage/ownership, e.g.
* when being copied or moved between threads.
*/
using Block = std::string_view;
/**
* Computes a suitable size for a reusable buffer that's intended to contain a block of
* event data, quantizing the input size so that small increases in payload size won't
* always result in reallocation.
*
* @param n The number of bytes that need to be stored in a buffer.
* @returns A number greater than or equal to N.
*/
inline size_t QuantizeBufferSize(const size_t n) {
// For values under 64kb, round up to the nearest power of two
const size_t threshold_kb = 64;
const size_t threshold = threshold_kb * static_cast<size_t>(1024);
if (n <= threshold) {
// Clamp the minimum buffer size to 256 bytes
size_t q = std::max(n, static_cast<size_t>(256));
// Decrement to handle values that are already a power of two
q--;
// Smear the highest set bit rightward, resulting in a value that contains all 1s
// starting from the most significant bit that was set in the original value; e.g.
// 01011001 -> 01111111; 00001101 -> 00001111
q |= q >> 1;
q |= q >> 2;
q |= q >> 4;
q |= q >> 8;
q |= q >> 16;
if constexpr (sizeof(size_t) > 4) {
q |= q >> 32;
}
// Increment to arrive at the resulting power of two;
// e.g. 01111111 -> 10000000; 00001111 -> 00010000
q++;
return q;
}
// For values above that threshold, increase in 16kb increments
const size_t snap_increment_kb = 16;
const size_t snap_increment = snap_increment_kb * static_cast<size_t>(1024);
return ((n + snap_increment - 1) / snap_increment) * snap_increment;
}
} // namespace datadog::impl