mirror of
https://github.com/roc-lang/roc.git
synced 2024-11-13 09:49:11 +03:00
Create new lowlevels for refcounting
This commit is contained in:
parent
c8278dcb1c
commit
6e5acadfea
@ -138,6 +138,7 @@ comptime {
|
||||
|
||||
comptime {
|
||||
exportUtilsFn(utils.test_panic, "test_panic");
|
||||
exportUtilsFn(utils.increfC, "incref");
|
||||
exportUtilsFn(utils.decrefC, "decref");
|
||||
exportUtilsFn(utils.decrefCheckNullC, "decref_check_null");
|
||||
|
||||
|
@ -104,6 +104,12 @@ pub const IntWidth = enum(u8) {
|
||||
I128 = 9,
|
||||
};
|
||||
|
||||
pub fn increfC(ptr_to_refcount: *isize, amount: isize) callconv(.C) void {
|
||||
var refcount = ptr_to_refcount.*;
|
||||
var masked_amount = if (refcount == REFCOUNT_MAX_ISIZE) 0 else amount;
|
||||
ptr_to_refcount.* = refcount + masked_amount;
|
||||
}
|
||||
|
||||
pub fn decrefC(
|
||||
bytes_or_null: ?[*]isize,
|
||||
alignment: u32,
|
||||
@ -261,3 +267,17 @@ pub const UpdateMode = enum(u8) {
|
||||
Immutable = 0,
|
||||
InPlace = 1,
|
||||
};
|
||||
|
||||
test "increfC, refcounted data" {
|
||||
var mock_rc: isize = REFCOUNT_ONE_ISIZE + 17;
|
||||
var ptr_to_refcount: *isize = &mock_rc;
|
||||
increfC(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);
|
||||
try std.testing.expectEqual(mock_rc, REFCOUNT_MAX_ISIZE);
|
||||
}
|
||||
|
@ -309,5 +309,6 @@ pub const DEC_MUL_WITH_OVERFLOW: &str = "roc_builtins.dec.mul_with_overflow";
|
||||
pub const DEC_DIV: &str = "roc_builtins.dec.div";
|
||||
|
||||
pub const UTILS_TEST_PANIC: &str = "roc_builtins.utils.test_panic";
|
||||
pub const UTILS_INCREF: &str = "roc_builtins.utils.incref";
|
||||
pub const UTILS_DECREF: &str = "roc_builtins.utils.decref";
|
||||
pub const UTILS_DECREF_CHECK_NULL: &str = "roc_builtins.utils.decref_check_null";
|
||||
|
@ -6020,6 +6020,10 @@ fn run_low_level<'a, 'ctx, 'env>(
|
||||
| ListAny | ListAll | ListFindUnsafe | DictWalk => {
|
||||
unreachable!("these are higher order, and are handled elsewhere")
|
||||
}
|
||||
|
||||
RefCountGetPtr | RefCountInc | RefCountDec => {
|
||||
unreachable!("LLVM backend does not use lowlevels for refcounting");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -370,6 +370,7 @@ pub fn decode_low_level<'a>(
|
||||
Not => code_builder.i32_eqz(),
|
||||
Hash => return NotImplemented,
|
||||
ExpectTrue => return NotImplemented,
|
||||
RefCountGetPtr | RefCountInc | RefCountDec => return NotImplemented,
|
||||
}
|
||||
Done
|
||||
}
|
||||
|
@ -115,6 +115,9 @@ pub enum LowLevel {
|
||||
Not,
|
||||
Hash,
|
||||
ExpectTrue,
|
||||
RefCountGetPtr,
|
||||
RefCountInc,
|
||||
RefCountDec,
|
||||
}
|
||||
|
||||
macro_rules! higher_order {
|
||||
|
@ -1008,6 +1008,10 @@ pub fn lowlevel_borrow_signature(arena: &Bump, op: LowLevel) -> &[bool] {
|
||||
SetFromList => arena.alloc_slice_copy(&[owned]),
|
||||
|
||||
ExpectTrue => arena.alloc_slice_copy(&[irrelevant]),
|
||||
|
||||
RefCountGetPtr | RefCountInc | RefCountDec => {
|
||||
unreachable!("Refcounting lowlevel calls are inserted *after* borrow checking");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user