add lowlevel to inc/dec a data pointer

This commit is contained in:
Folkert 2023-04-28 15:30:23 +02:00
parent a61e7a696d
commit cf54304cf4
No known key found for this signature in database
GPG key ID: 1F17F6FFD112B97C
13 changed files with 90 additions and 28 deletions

View file

@ -147,7 +147,7 @@ const Refcount = enum {
const RC_TYPE = Refcount.normal;
pub fn increfC(ptr_to_refcount: *isize, amount: isize) callconv(.C) void {
pub fn increfRcPtrC(ptr_to_refcount: *isize, amount: isize) callconv(.C) void {
if (RC_TYPE == Refcount.none) return;
// Ensure that the refcount is not whole program lifetime.
if (ptr_to_refcount.* != REFCOUNT_MAX_ISIZE) {
@ -165,7 +165,7 @@ pub fn increfC(ptr_to_refcount: *isize, amount: isize) callconv(.C) void {
}
}
pub fn decrefC(
pub fn decrefRcPtrC(
bytes_or_null: ?[*]isize,
alignment: u32,
) callconv(.C) void {
@ -188,6 +188,36 @@ pub fn decrefCheckNullC(
}
}
pub fn decrefDataPtrC(
bytes_or_null: ?[*]isize,
alignment: u32,
) callconv(.C) void {
var bytes = bytes_or_null orelse return;
const ptr = @ptrToInt(bytes);
const tag_mask: usize = if (@sizeOf(usize) == 8) 0b111 else 0b11;
const masked_ptr = ptr & ~tag_mask;
const isizes: [*]isize = @intToPtr([*]isize, masked_ptr);
return decrefRcPtrC(isizes - 1, alignment);
}
pub fn increfDataPtrC(
bytes_or_null: ?[*]isize,
inc_amount: isize,
) callconv(.C) void {
var bytes = bytes_or_null orelse return;
const ptr = @ptrToInt(bytes);
const tag_mask: usize = if (@sizeOf(usize) == 8) 0b111 else 0b11;
const masked_ptr = ptr & ~tag_mask;
const isizes: *isize = @intToPtr(*isize, masked_ptr - @sizeOf(usize));
return increfRcPtrC(isizes, inc_amount);
}
pub fn decref(
bytes_or_null: ?[*]u8,
data_bytes: usize,
@ -363,13 +393,13 @@ pub const UpdateMode = enum(u8) {
test "increfC, refcounted data" {
var mock_rc: isize = REFCOUNT_ONE_ISIZE + 17;
var ptr_to_refcount: *isize = &mock_rc;
increfC(ptr_to_refcount, 2);
increfRcPtrC(ptr_to_refcount, 2);
try std.testing.expectEqual(mock_rc, REFCOUNT_ONE_ISIZE + 19);
}
test "increfC, static data" {
var mock_rc: isize = REFCOUNT_MAX_ISIZE;
var ptr_to_refcount: *isize = &mock_rc;
increfC(ptr_to_refcount, 2);
increfRcPtrC(ptr_to_refcount, 2);
try std.testing.expectEqual(mock_rc, REFCOUNT_MAX_ISIZE);
}