aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorgingerBill <bill@gingerbill.org>2025-03-31 10:51:02 +0100
committergingerBill <bill@gingerbill.org>2025-03-31 10:51:02 +0100
commit70ddb74e402fe5c2c1b139c3e7a66a9eaf566930 (patch)
tree9d1df3f254475d3999dca6c5aaa49fb5dccb8e53
parentdcb683927ea9ebe6f53124ce56700ece68dce164 (diff)
Add `mem.make_over_aligned`
-rw-r--r--core/mem/alloc.odin28
-rw-r--r--core/mem/mem.odin2
2 files changed, 29 insertions, 1 deletions
diff --git a/core/mem/alloc.odin b/core/mem/alloc.odin
index 6dcfb7888..48cc39245 100644
--- a/core/mem/alloc.odin
+++ b/core/mem/alloc.odin
@@ -888,6 +888,34 @@ make_aligned :: proc(
return runtime.make_aligned(T, len, alignment, allocator, loc)
}
+
+/*
+Allocate a new slice with alignment for allocators that might not support the
+specified alignment requirement.
+
+This procedure allocates a new slice of type `T` with length `len`, aligned
+on a boundary specified by `alignment` from an allocator specified by
+`allocator`, and returns the allocated slice.
+
+The user should `delete` the return `original_data` slice not the typed `slice`.
+*/
+@(require_results)
+make_over_aligned :: proc(
+ $T: typeid/[]$E,
+ #any_int len: int,
+ alignment: int,
+ allocator: runtime.Allocator,
+ loc := #caller_location,
+) -> (slice: T, original_data: []byte, err: Allocator_Error) {
+ size := size_of(E)*len + alignment-1
+ original_data, err = runtime.make([]byte, size, allocator, loc)
+ if err == nil {
+ ptr := align_forward(raw_data(original_data), uintptr(alignment))
+ slice = ([^]E)(ptr)[:len]
+ }
+ return
+}
+
/*
Allocate a new slice.
diff --git a/core/mem/mem.odin b/core/mem/mem.odin
index d578dd477..5789309f7 100644
--- a/core/mem/mem.odin
+++ b/core/mem/mem.odin
@@ -1,4 +1,4 @@
-#package mem
+package mem
import "base:runtime"
import "base:intrinsics"