tigerbeetle-node 0.11.3 → 0.11.5
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/.client.node.sha256 +1 -1
- package/package.json +1 -1
- package/src/node.zig +10 -5
- package/src/tigerbeetle/src/benchmark.zig +4 -4
- package/src/tigerbeetle/src/c/tb_client/context.zig +6 -6
- package/src/tigerbeetle/src/c/tb_client/echo_client.zig +2 -2
- package/src/tigerbeetle/src/c/tb_client/thread.zig +0 -1
- package/src/tigerbeetle/src/c/tb_client.h +97 -111
- package/src/tigerbeetle/src/c/tb_client.zig +30 -19
- package/src/tigerbeetle/src/c/tb_client_header.zig +218 -0
- package/src/tigerbeetle/src/c/test.zig +14 -14
- package/src/tigerbeetle/src/cli.zig +12 -12
- package/src/tigerbeetle/src/config.zig +183 -379
- package/src/tigerbeetle/src/constants.zig +394 -0
- package/src/tigerbeetle/src/demo.zig +4 -4
- package/src/tigerbeetle/src/ewah_fuzz.zig +2 -0
- package/src/tigerbeetle/src/io/darwin.zig +4 -4
- package/src/tigerbeetle/src/io/linux.zig +6 -6
- package/src/tigerbeetle/src/io/windows.zig +4 -4
- package/src/tigerbeetle/src/lsm/bloom_filter.zig +1 -1
- package/src/tigerbeetle/src/lsm/compaction.zig +15 -10
- package/src/tigerbeetle/src/lsm/forest.zig +2 -2
- package/src/tigerbeetle/src/lsm/forest_fuzz.zig +18 -15
- package/src/tigerbeetle/src/lsm/grid.zig +5 -5
- package/src/tigerbeetle/src/lsm/groove.zig +8 -42
- package/src/tigerbeetle/src/lsm/level_iterator.zig +2 -2
- package/src/tigerbeetle/src/lsm/manifest.zig +19 -23
- package/src/tigerbeetle/src/lsm/manifest_level.zig +2 -2
- package/src/tigerbeetle/src/lsm/manifest_log.zig +8 -8
- package/src/tigerbeetle/src/lsm/manifest_log_fuzz.zig +25 -12
- package/src/tigerbeetle/src/lsm/posted_groove.zig +4 -15
- package/src/tigerbeetle/src/lsm/segmented_array_benchmark.zig +13 -13
- package/src/tigerbeetle/src/lsm/set_associative_cache.zig +2 -2
- package/src/tigerbeetle/src/lsm/table.zig +43 -35
- package/src/tigerbeetle/src/lsm/table_immutable.zig +4 -4
- package/src/tigerbeetle/src/lsm/table_iterator.zig +17 -9
- package/src/tigerbeetle/src/lsm/table_mutable.zig +3 -3
- package/src/tigerbeetle/src/lsm/test.zig +6 -6
- package/src/tigerbeetle/src/lsm/tree.zig +75 -47
- package/src/tigerbeetle/src/lsm/tree_fuzz.zig +27 -28
- package/src/tigerbeetle/src/main.zig +32 -23
- package/src/tigerbeetle/src/message_bus.zig +25 -25
- package/src/tigerbeetle/src/message_pool.zig +17 -17
- package/src/tigerbeetle/src/simulator.zig +7 -12
- package/src/tigerbeetle/src/state_machine.zig +582 -1806
- package/src/tigerbeetle/src/storage.zig +12 -12
- package/src/tigerbeetle/src/test/accounting/auditor.zig +2 -2
- package/src/tigerbeetle/src/test/accounting/workload.zig +5 -5
- package/src/tigerbeetle/src/test/cluster.zig +8 -8
- package/src/tigerbeetle/src/test/conductor.zig +6 -5
- package/src/tigerbeetle/src/test/fuzz.zig +19 -0
- package/src/tigerbeetle/src/test/message_bus.zig +0 -2
- package/src/tigerbeetle/src/test/network.zig +5 -5
- package/src/tigerbeetle/src/test/state_checker.zig +2 -2
- package/src/tigerbeetle/src/test/storage.zig +54 -51
- package/src/tigerbeetle/src/test/storage_checker.zig +3 -3
- package/src/tigerbeetle/src/test/table.zig +226 -0
- package/src/tigerbeetle/src/time.zig +0 -1
- package/src/tigerbeetle/src/tracer.zig +402 -214
- package/src/tigerbeetle/src/unit_tests.zig +1 -0
- package/src/tigerbeetle/src/vsr/client.zig +5 -5
- package/src/tigerbeetle/src/vsr/clock.zig +9 -8
- package/src/tigerbeetle/src/vsr/journal.zig +47 -47
- package/src/tigerbeetle/src/vsr/journal_format_fuzz.zig +13 -11
- package/src/tigerbeetle/src/vsr/replica.zig +56 -54
- package/src/tigerbeetle/src/vsr/replica_format.zig +8 -8
- package/src/tigerbeetle/src/vsr/superblock.zig +55 -55
- package/src/tigerbeetle/src/vsr/superblock_client_table.zig +9 -9
- package/src/tigerbeetle/src/vsr/superblock_free_set.zig +4 -3
- package/src/tigerbeetle/src/vsr/superblock_free_set_fuzz.zig +2 -0
- package/src/tigerbeetle/src/vsr/superblock_fuzz.zig +9 -6
- package/src/tigerbeetle/src/vsr/superblock_manifest.zig +5 -5
- package/src/tigerbeetle/src/vsr/superblock_quorums_fuzz.zig +2 -0
- package/src/tigerbeetle/src/vsr.zig +20 -20
|
@@ -0,0 +1,218 @@
|
|
|
1
|
+
const std = @import("std");
|
|
2
|
+
const tb = @import("../tigerbeetle.zig");
|
|
3
|
+
const tb_client = @import("tb_client.zig");
|
|
4
|
+
|
|
5
|
+
const type_mappings = .{
|
|
6
|
+
.{ tb.AccountFlags, "TB_ACCOUNT_FLAGS" },
|
|
7
|
+
.{ tb.Account, "tb_account_t" },
|
|
8
|
+
.{ tb.TransferFlags, "TB_TRANSFER_FLAGS" },
|
|
9
|
+
.{ tb.Transfer, "tb_transfer_t" },
|
|
10
|
+
.{ tb.CreateAccountResult, "TB_CREATE_ACCOUNT_RESULT" },
|
|
11
|
+
.{ tb.CreateTransferResult, "TB_CREATE_TRANSFER_RESULT" },
|
|
12
|
+
.{ tb.CreateAccountsResult, "tb_create_accounts_result_t" },
|
|
13
|
+
.{ tb.CreateTransfersResult, "tb_create_transfers_result_t" },
|
|
14
|
+
.{ tb_client.tb_operation_t, "TB_OPERATION" },
|
|
15
|
+
.{ tb_client.tb_packet_status_t, "TB_PACKET_STATUS" },
|
|
16
|
+
.{ tb_client.tb_packet_t, "tb_packet_t" },
|
|
17
|
+
.{ tb_client.tb_packet_list_t, "tb_packet_list_t" },
|
|
18
|
+
.{ tb_client.tb_client_t, "tb_client_t" },
|
|
19
|
+
.{ tb_client.tb_status_t, "TB_STATUS" },
|
|
20
|
+
};
|
|
21
|
+
|
|
22
|
+
fn resolve_c_type(comptime Type: type) []const u8 {
|
|
23
|
+
switch (@typeInfo(Type)) {
|
|
24
|
+
.Array => |info| return resolve_c_type(info.child),
|
|
25
|
+
.Enum => |info| return resolve_c_type(info.tag_type),
|
|
26
|
+
.Struct => return resolve_c_type(std.meta.Int(.unsigned, @bitSizeOf(Type))),
|
|
27
|
+
.Int => |info| {
|
|
28
|
+
std.debug.assert(info.signedness == .unsigned);
|
|
29
|
+
return switch (info.bits) {
|
|
30
|
+
8 => "uint8_t",
|
|
31
|
+
16 => "uint16_t",
|
|
32
|
+
32 => "uint32_t",
|
|
33
|
+
64 => "uint64_t",
|
|
34
|
+
128 => "tb_uint128_t",
|
|
35
|
+
else => @compileError("invalid int type"),
|
|
36
|
+
};
|
|
37
|
+
},
|
|
38
|
+
.Optional => |info| switch (@typeInfo(info.child)) {
|
|
39
|
+
.Pointer => return resolve_c_type(info.child),
|
|
40
|
+
else => @compileError("Unsupported optional type: " ++ @typeName(Type)),
|
|
41
|
+
},
|
|
42
|
+
.Pointer => |info| {
|
|
43
|
+
std.debug.assert(info.size != .Slice);
|
|
44
|
+
std.debug.assert(!info.is_allowzero);
|
|
45
|
+
|
|
46
|
+
inline for (type_mappings) |type_mapping| {
|
|
47
|
+
const ZigType = type_mapping[0];
|
|
48
|
+
const c_name = type_mapping[1];
|
|
49
|
+
|
|
50
|
+
if (info.child == ZigType) {
|
|
51
|
+
const prefix = if (@typeInfo(ZigType) == .Struct) "struct " else "";
|
|
52
|
+
return prefix ++ c_name ++ "*";
|
|
53
|
+
}
|
|
54
|
+
}
|
|
55
|
+
|
|
56
|
+
return resolve_c_type(info.child) ++ "*";
|
|
57
|
+
},
|
|
58
|
+
.Void, .Opaque => return "void",
|
|
59
|
+
else => @compileError("Unhandled type: " ++ @typeName(Type)),
|
|
60
|
+
}
|
|
61
|
+
}
|
|
62
|
+
|
|
63
|
+
fn to_uppercase(comptime input: []const u8) []const u8 {
|
|
64
|
+
comptime var output: [input.len]u8 = undefined;
|
|
65
|
+
inline for (output) |*char, i| {
|
|
66
|
+
char.* = input[i];
|
|
67
|
+
char.* -= 32 * @as(u8, @boolToInt(char.* >= 'a' and char.* <= 'z'));
|
|
68
|
+
}
|
|
69
|
+
return &output;
|
|
70
|
+
}
|
|
71
|
+
|
|
72
|
+
fn emit_enum(
|
|
73
|
+
buffer: *std.ArrayList(u8),
|
|
74
|
+
comptime type_info: anytype,
|
|
75
|
+
comptime c_name: []const u8,
|
|
76
|
+
comptime value_fmt: []const u8,
|
|
77
|
+
comptime skip_fields: []const []const u8,
|
|
78
|
+
) !void {
|
|
79
|
+
var suffix_pos = std.mem.lastIndexOf(u8, c_name, "_").?;
|
|
80
|
+
if (std.mem.count(u8, c_name, "_") == 1) suffix_pos = c_name.len;
|
|
81
|
+
|
|
82
|
+
try buffer.writer().print("typedef enum {s} {{\n", .{c_name});
|
|
83
|
+
|
|
84
|
+
inline for (type_info.fields) |field, i| {
|
|
85
|
+
comptime var skip = false;
|
|
86
|
+
inline for (skip_fields) |sf| {
|
|
87
|
+
skip = skip or comptime std.mem.eql(u8, sf, field.name);
|
|
88
|
+
}
|
|
89
|
+
|
|
90
|
+
if (!skip) {
|
|
91
|
+
try buffer.writer().print(" {s}_{s} = " ++ value_fmt ++ ",\n", .{
|
|
92
|
+
c_name[0..suffix_pos],
|
|
93
|
+
to_uppercase(field.name),
|
|
94
|
+
i,
|
|
95
|
+
});
|
|
96
|
+
}
|
|
97
|
+
}
|
|
98
|
+
|
|
99
|
+
try buffer.writer().print("}} {s};\n\n", .{c_name});
|
|
100
|
+
}
|
|
101
|
+
|
|
102
|
+
fn emit_struct(
|
|
103
|
+
buffer: *std.ArrayList(u8),
|
|
104
|
+
comptime type_info: anytype,
|
|
105
|
+
comptime c_name: []const u8,
|
|
106
|
+
) !void {
|
|
107
|
+
try buffer.writer().print("typedef struct {s} {{\n", .{c_name});
|
|
108
|
+
|
|
109
|
+
inline for (type_info.fields) |field| {
|
|
110
|
+
try buffer.writer().print(" {s} {s}", .{
|
|
111
|
+
resolve_c_type(field.field_type),
|
|
112
|
+
field.name,
|
|
113
|
+
});
|
|
114
|
+
|
|
115
|
+
switch (@typeInfo(field.field_type)) {
|
|
116
|
+
.Array => |array| try buffer.writer().print("[{d}]", .{array.len}),
|
|
117
|
+
else => {},
|
|
118
|
+
}
|
|
119
|
+
|
|
120
|
+
try buffer.writer().print(";\n", .{});
|
|
121
|
+
}
|
|
122
|
+
|
|
123
|
+
try buffer.writer().print("}} {s};\n\n", .{c_name});
|
|
124
|
+
}
|
|
125
|
+
|
|
126
|
+
pub fn main() !void {
|
|
127
|
+
@setEvalBranchQuota(100_000);
|
|
128
|
+
|
|
129
|
+
var arena = std.heap.ArenaAllocator.init(std.heap.page_allocator);
|
|
130
|
+
defer arena.deinit();
|
|
131
|
+
const allocator = arena.allocator();
|
|
132
|
+
|
|
133
|
+
var buffer = std.ArrayList(u8).init(allocator);
|
|
134
|
+
try buffer.writer().print(
|
|
135
|
+
\\ //////////////////////////////////////////////////////////
|
|
136
|
+
\\ // This file was auto-generated by tb_client_header.zig //
|
|
137
|
+
\\ // Do not manually modify. //
|
|
138
|
+
\\ //////////////////////////////////////////////////////////
|
|
139
|
+
\\
|
|
140
|
+
\\#ifndef TB_CLIENT_H
|
|
141
|
+
\\#define TB_CLIENT_H
|
|
142
|
+
\\
|
|
143
|
+
\\#include <stddef.h>
|
|
144
|
+
\\#include <stdint.h>
|
|
145
|
+
\\#include <stdbool.h>
|
|
146
|
+
\\
|
|
147
|
+
\\typedef __uint128_t tb_uint128_t;
|
|
148
|
+
\\
|
|
149
|
+
\\
|
|
150
|
+
, .{});
|
|
151
|
+
|
|
152
|
+
// Emit C type declarations.
|
|
153
|
+
inline for (type_mappings) |type_mapping| {
|
|
154
|
+
const ZigType = type_mapping[0];
|
|
155
|
+
const c_name = type_mapping[1];
|
|
156
|
+
|
|
157
|
+
switch (@typeInfo(ZigType)) {
|
|
158
|
+
.Struct => |info| switch (info.layout) {
|
|
159
|
+
.Auto => @compileError("Invalid C struct type: " ++ @typeName(ZigType)),
|
|
160
|
+
.Packed => try emit_enum(&buffer, info, c_name, "1 << {d}", &.{"padding"}),
|
|
161
|
+
.Extern => try emit_struct(&buffer, info, c_name),
|
|
162
|
+
},
|
|
163
|
+
.Enum => |info| {
|
|
164
|
+
comptime var skip: []const []const u8 = &.{};
|
|
165
|
+
if (ZigType == tb_client.tb_operation_t) {
|
|
166
|
+
skip = &.{ "reserved", "root", "register" };
|
|
167
|
+
}
|
|
168
|
+
|
|
169
|
+
try emit_enum(&buffer, info, c_name, "{d}", skip);
|
|
170
|
+
},
|
|
171
|
+
else => try buffer.writer().print("typedef {s} {s}; \n\n", .{
|
|
172
|
+
resolve_c_type(ZigType),
|
|
173
|
+
c_name,
|
|
174
|
+
}),
|
|
175
|
+
}
|
|
176
|
+
}
|
|
177
|
+
|
|
178
|
+
// Emit C function declarations.
|
|
179
|
+
// TODO: use `std.meta.declaractions` and generate with pub + export functions.
|
|
180
|
+
// Zig 0.9.1 has `decl.data.Fn.arg_names` but it's currently/incorrectly a zero-sized slice.
|
|
181
|
+
try buffer.writer().print(
|
|
182
|
+
\\TB_STATUS tb_client_init(
|
|
183
|
+
\\ tb_client_t* out_client,
|
|
184
|
+
\\ struct tb_packet_list_t* out_packets,
|
|
185
|
+
\\ uint32_t cluster_id,
|
|
186
|
+
\\ const char* address_ptr,
|
|
187
|
+
\\ uint32_t address_len,
|
|
188
|
+
\\ uint32_t packets_count,
|
|
189
|
+
\\ uintptr_t on_completion_ctx,
|
|
190
|
+
\\ void (*on_completion_fn)(uintptr_t, tb_client_t, tb_packet_t*, const uint8_t*, uint32_t)
|
|
191
|
+
\\);
|
|
192
|
+
\\
|
|
193
|
+
\\TB_STATUS tb_client_init_echo(
|
|
194
|
+
\\ tb_client_t* out_client,
|
|
195
|
+
\\ struct tb_packet_list_t* out_packets,
|
|
196
|
+
\\ uint32_t cluster_id,
|
|
197
|
+
\\ const char* address_ptr,
|
|
198
|
+
\\ uint32_t address_len,
|
|
199
|
+
\\ uint32_t packets_count,
|
|
200
|
+
\\ uintptr_t on_completion_ctx,
|
|
201
|
+
\\ void (*on_completion_fn)(uintptr_t, tb_client_t, tb_packet_t*, const uint8_t*, uint32_t)
|
|
202
|
+
\\);
|
|
203
|
+
\\
|
|
204
|
+
\\void tb_client_submit(
|
|
205
|
+
\\ tb_client_t client,
|
|
206
|
+
\\ struct tb_packet_list_t* packets
|
|
207
|
+
\\);
|
|
208
|
+
\\
|
|
209
|
+
\\void tb_client_deinit(
|
|
210
|
+
\\ tb_client_t client
|
|
211
|
+
\\);
|
|
212
|
+
\\
|
|
213
|
+
\\
|
|
214
|
+
, .{});
|
|
215
|
+
|
|
216
|
+
try buffer.writer().print("#endif // TB_CLIENT_H\n\n", .{});
|
|
217
|
+
try std.fs.cwd().writeFile("src/c/tb_client.h", buffer.items);
|
|
218
|
+
}
|
|
@@ -6,7 +6,7 @@ const testing = std.testing;
|
|
|
6
6
|
const c = @cImport(@cInclude("tb_client.h"));
|
|
7
7
|
|
|
8
8
|
const util = @import("../util.zig");
|
|
9
|
-
const
|
|
9
|
+
const constants = @import("../constants.zig");
|
|
10
10
|
const Packet = @import("tb_client/packet.zig").Packet;
|
|
11
11
|
|
|
12
12
|
const Mutex = std.Thread.Mutex;
|
|
@@ -91,10 +91,10 @@ const Completion = struct {
|
|
|
91
91
|
// 3. the data marshaling is correct, and exactly the same data sent was received back.
|
|
92
92
|
test "c_client echo" {
|
|
93
93
|
// Using the create_accounts operation for this test.
|
|
94
|
-
const RequestContext = RequestContextType(
|
|
95
|
-
const create_accounts_operation: u8 = c.
|
|
94
|
+
const RequestContext = RequestContextType(constants.message_body_size_max);
|
|
95
|
+
const create_accounts_operation: u8 = c.TB_OPERATION_CREATE_ACCOUNTS;
|
|
96
96
|
const event_size = @sizeOf(c.tb_account_t);
|
|
97
|
-
const event_request_max = @divFloor(
|
|
97
|
+
const event_request_max = @divFloor(constants.message_body_size_max, event_size);
|
|
98
98
|
|
|
99
99
|
// Initializing an echo client for testing purposes.
|
|
100
100
|
// We ensure that the retry mechanism is being tested
|
|
@@ -103,7 +103,7 @@ test "c_client echo" {
|
|
|
103
103
|
var tb_packet_list: c.tb_packet_list_t = undefined;
|
|
104
104
|
const cluster_id = 0;
|
|
105
105
|
const address = "3000";
|
|
106
|
-
const packets_count: u32 =
|
|
106
|
+
const packets_count: u32 = constants.client_request_queue_max * 2;
|
|
107
107
|
const tb_context: usize = 42;
|
|
108
108
|
const result = c.tb_client_init_echo(
|
|
109
109
|
&tb_client,
|
|
@@ -221,7 +221,7 @@ test "c_client tb_status" {
|
|
|
221
221
|
// More addresses thant "replicas_max" should return "TB_STATUS_ADDRESS_LIMIT_EXCEEDED":
|
|
222
222
|
try assert_status(
|
|
223
223
|
1,
|
|
224
|
-
("3000," **
|
|
224
|
+
("3000," ** constants.replicas_max) ++ "3001",
|
|
225
225
|
c.TB_STATUS_ADDRESS_LIMIT_EXCEEDED,
|
|
226
226
|
);
|
|
227
227
|
|
|
@@ -234,7 +234,7 @@ test "c_client tb_status" {
|
|
|
234
234
|
|
|
235
235
|
// Asserts the validation rules associated with the "TB_PACKET_STATUS" enum.
|
|
236
236
|
test "c_client tb_packet_status" {
|
|
237
|
-
const RequestContext = RequestContextType(
|
|
237
|
+
const RequestContext = RequestContextType(constants.message_body_size_max);
|
|
238
238
|
|
|
239
239
|
var tb_client: c.tb_client_t = undefined;
|
|
240
240
|
var tb_packet_list: c.tb_packet_list_t = undefined;
|
|
@@ -299,12 +299,12 @@ test "c_client tb_packet_status" {
|
|
|
299
299
|
|
|
300
300
|
var packet_list = @ptrCast(*Packet.List, &tb_packet_list);
|
|
301
301
|
|
|
302
|
-
// Messages larger than
|
|
302
|
+
// Messages larger than constants.message_body_size_max should return "too_much_data":
|
|
303
303
|
try assert_result(
|
|
304
304
|
tb_client,
|
|
305
305
|
packet_list,
|
|
306
|
-
c.
|
|
307
|
-
|
|
306
|
+
c.TB_OPERATION_CREATE_TRANSFERS,
|
|
307
|
+
constants.message_body_size_max + @sizeOf(c.tb_transfer_t),
|
|
308
308
|
c.TB_PACKET_TOO_MUCH_DATA,
|
|
309
309
|
);
|
|
310
310
|
|
|
@@ -343,28 +343,28 @@ test "c_client tb_packet_status" {
|
|
|
343
343
|
try assert_result(
|
|
344
344
|
tb_client,
|
|
345
345
|
packet_list,
|
|
346
|
-
c.
|
|
346
|
+
c.TB_OPERATION_CREATE_ACCOUNTS,
|
|
347
347
|
0,
|
|
348
348
|
c.TB_PACKET_INVALID_DATA_SIZE,
|
|
349
349
|
);
|
|
350
350
|
try assert_result(
|
|
351
351
|
tb_client,
|
|
352
352
|
packet_list,
|
|
353
|
-
c.
|
|
353
|
+
c.TB_OPERATION_CREATE_TRANSFERS,
|
|
354
354
|
@sizeOf(c.tb_transfer_t) - 1,
|
|
355
355
|
c.TB_PACKET_INVALID_DATA_SIZE,
|
|
356
356
|
);
|
|
357
357
|
try assert_result(
|
|
358
358
|
tb_client,
|
|
359
359
|
packet_list,
|
|
360
|
-
c.
|
|
360
|
+
c.TB_OPERATION_LOOKUP_TRANSFERS,
|
|
361
361
|
@sizeOf(u128) + 1,
|
|
362
362
|
c.TB_PACKET_INVALID_DATA_SIZE,
|
|
363
363
|
);
|
|
364
364
|
try assert_result(
|
|
365
365
|
tb_client,
|
|
366
366
|
packet_list,
|
|
367
|
-
c.
|
|
367
|
+
c.TB_OPERATION_LOOKUP_ACCOUNTS,
|
|
368
368
|
@sizeOf(u128) * 2.5,
|
|
369
369
|
c.TB_PACKET_INVALID_DATA_SIZE,
|
|
370
370
|
);
|
|
@@ -7,7 +7,7 @@ const meta = std.meta;
|
|
|
7
7
|
const net = std.net;
|
|
8
8
|
const os = std.os;
|
|
9
9
|
|
|
10
|
-
const
|
|
10
|
+
const constants = @import("constants.zig");
|
|
11
11
|
const tigerbeetle = @import("tigerbeetle.zig");
|
|
12
12
|
const vsr = @import("vsr.zig");
|
|
13
13
|
const IO = @import("io.zig").IO;
|
|
@@ -72,8 +72,8 @@ const usage = fmt.comptimePrint(
|
|
|
72
72
|
\\ tigerbeetle version --verbose
|
|
73
73
|
\\
|
|
74
74
|
, .{
|
|
75
|
-
.default_address =
|
|
76
|
-
.default_port =
|
|
75
|
+
.default_address = constants.address,
|
|
76
|
+
.default_port = constants.port,
|
|
77
77
|
});
|
|
78
78
|
|
|
79
79
|
pub const Command = union(enum) {
|
|
@@ -206,17 +206,17 @@ pub fn parse_args(allocator: std.mem.Allocator) !Command {
|
|
|
206
206
|
.cache_accounts = parse_size_to_count(
|
|
207
207
|
tigerbeetle.Account,
|
|
208
208
|
cache_accounts,
|
|
209
|
-
|
|
209
|
+
constants.cache_accounts_max,
|
|
210
210
|
),
|
|
211
211
|
.cache_transfers = parse_size_to_count(
|
|
212
212
|
tigerbeetle.Transfer,
|
|
213
213
|
cache_transfers,
|
|
214
|
-
|
|
214
|
+
constants.cache_transfers_max,
|
|
215
215
|
),
|
|
216
216
|
.cache_transfers_posted = parse_size_to_count(
|
|
217
217
|
u256, // TODO(#264): Use actual type here, once exposed.
|
|
218
218
|
cache_transfers_posted,
|
|
219
|
-
|
|
219
|
+
constants.cache_transfers_posted_max,
|
|
220
220
|
),
|
|
221
221
|
.path = path orelse fatal("required: <path>", .{}),
|
|
222
222
|
},
|
|
@@ -255,11 +255,11 @@ fn parse_cluster(raw_cluster: []const u8) u32 {
|
|
|
255
255
|
|
|
256
256
|
/// Parse and allocate the addresses returning a slice into that array.
|
|
257
257
|
fn parse_addresses(allocator: std.mem.Allocator, raw_addresses: []const u8) []net.Address {
|
|
258
|
-
return vsr.parse_addresses(allocator, raw_addresses,
|
|
258
|
+
return vsr.parse_addresses(allocator, raw_addresses, constants.replicas_max) catch |err| switch (err) {
|
|
259
259
|
error.AddressHasTrailingComma => fatal("--addresses: invalid trailing comma", .{}),
|
|
260
260
|
error.AddressLimitExceeded => {
|
|
261
261
|
fatal("--addresses: too many addresses, at most {d} are allowed", .{
|
|
262
|
-
|
|
262
|
+
constants.replicas_max,
|
|
263
263
|
});
|
|
264
264
|
},
|
|
265
265
|
error.AddressHasMoreThanOneColon => {
|
|
@@ -351,7 +351,7 @@ fn parse_size_to_count(comptime T: type, string_opt: ?[]const u8, comptime defau
|
|
|
351
351
|
const count = math.cast(u32, count_u64) catch |err| switch (err) {
|
|
352
352
|
error.Overflow => fatal("size value is too large: '{s}'", .{string}),
|
|
353
353
|
};
|
|
354
|
-
if (count < 2048) fatal("size value is too small: '{s}'", .{string});
|
|
354
|
+
if (count > 0 and count < 2048) fatal("size value is too small: '{s}'", .{string});
|
|
355
355
|
assert(count * @sizeOf(T) <= byte_size);
|
|
356
356
|
|
|
357
357
|
result = count;
|
|
@@ -359,14 +359,14 @@ fn parse_size_to_count(comptime T: type, string_opt: ?[]const u8, comptime defau
|
|
|
359
359
|
|
|
360
360
|
// SetAssociativeCache requires a power-of-two cardinality and a minimal
|
|
361
361
|
// size.
|
|
362
|
-
assert(result >= 2048);
|
|
363
|
-
assert(math.isPowerOfTwo(result));
|
|
362
|
+
assert(result == 0 or result >= 2048);
|
|
363
|
+
assert(result == 0 or math.isPowerOfTwo(result));
|
|
364
364
|
|
|
365
365
|
return result;
|
|
366
366
|
}
|
|
367
367
|
|
|
368
368
|
fn parse_replica(raw_replica: []const u8) u8 {
|
|
369
|
-
comptime assert(
|
|
369
|
+
comptime assert(constants.replicas_max <= std.math.maxInt(u8));
|
|
370
370
|
const replica = fmt.parseUnsigned(u8, raw_replica, 10) catch |err| switch (err) {
|
|
371
371
|
error.Overflow => fatal("--replica: value exceeds an 8-bit unsigned integer", .{}),
|
|
372
372
|
error.InvalidCharacter => fatal("--replica: value contains an invalid character", .{}),
|