working on grime a bit
This commit is contained in:
@@ -177,9 +177,6 @@ odin_allocator_mode_to_allocator_op :: #force_inline proc "contextless" (mode: O
|
||||
panic_contextless("Impossible path")
|
||||
}
|
||||
|
||||
// TODO(Ed): Change to DEFAULT_ALIGNMENT
|
||||
MEMORY_ALIGNMENT_DEFAULT :: 2 * size_of(rawptr)
|
||||
|
||||
allocatorinfo :: #force_inline proc(ainfo := context.allocator) -> AllocatorInfo { return transmute(AllocatorInfo) ainfo }
|
||||
allocator :: #force_inline proc(ainfo: AllocatorInfo) -> Odin_Allocator { return transmute(Odin_Allocator) ainfo }
|
||||
|
||||
@@ -202,11 +199,10 @@ mem_rewind :: proc(ainfo := context.allocator, save_point: AllocatorSP, loc := #
|
||||
}
|
||||
mem_save_point :: proc(ainfo := context.allocator, loc := #caller_location) -> AllocatorSP {
|
||||
assert(ainfo.procedure != nil)
|
||||
out: AllocatorProc_Out
|
||||
resolve_allocator_proc(ainfo.procedure)({data = ainfo.data, op = .SavePoint, loc = loc}, & out)
|
||||
out: AllocatorProc_Out; resolve_allocator_proc(ainfo.procedure)({data = ainfo.data, op = .SavePoint, loc = loc}, & out)
|
||||
return out.save_point
|
||||
}
|
||||
mem_alloc :: proc(size: int, alignment: int = MEMORY_ALIGNMENT_DEFAULT, no_zero: bool = false, ainfo: $Type = context.allocator, loc := #caller_location) -> ([]byte, AllocatorError) {
|
||||
mem_alloc :: proc(size: int, alignment: int = DEFAULT_ALIGNMENT, no_zero: bool = false, ainfo: $Type = context.allocator, loc := #caller_location) -> ([]byte, AllocatorError) {
|
||||
assert(ainfo.procedure != nil)
|
||||
input := AllocatorProc_In {
|
||||
data = ainfo.data,
|
||||
@@ -215,11 +211,10 @@ mem_alloc :: proc(size: int, alignment: int = MEMORY_ALIGNMENT_DEFAULT, no_zero:
|
||||
alignment = alignment,
|
||||
loc = loc,
|
||||
}
|
||||
output: AllocatorProc_Out
|
||||
resolve_allocator_proc(ainfo.procedure)(input, & output)
|
||||
output: AllocatorProc_Out; resolve_allocator_proc(ainfo.procedure)(input, & output)
|
||||
return output.allocation, output.error
|
||||
}
|
||||
mem_grow :: proc(mem: []byte, size: int, alignment: int = MEMORY_ALIGNMENT_DEFAULT, no_zero: bool = false, ainfo := context.allocator, loc := #caller_location) -> ([]byte, AllocatorError) {
|
||||
mem_grow :: proc(mem: []byte, size: int, alignment: int = DEFAULT_ALIGNMENT, no_zero: bool = false, ainfo := context.allocator, loc := #caller_location) -> ([]byte, AllocatorError) {
|
||||
assert(ainfo.procedure != nil)
|
||||
input := AllocatorProc_In {
|
||||
data = ainfo.data,
|
||||
@@ -229,11 +224,10 @@ mem_grow :: proc(mem: []byte, size: int, alignment: int = MEMORY_ALIGNMENT_DEFAU
|
||||
old_allocation = mem,
|
||||
loc = loc,
|
||||
}
|
||||
output: AllocatorProc_Out
|
||||
resolve_allocator_proc(ainfo.procedure)(input, & output)
|
||||
output: AllocatorProc_Out; resolve_allocator_proc(ainfo.procedure)(input, & output)
|
||||
return output.allocation, output.error
|
||||
}
|
||||
mem_resize :: proc(mem: []byte, size: int, alignment: int = MEMORY_ALIGNMENT_DEFAULT, no_zero: bool = false, ainfo := context.allocator, loc := #caller_location) -> ([]byte, AllocatorError) {
|
||||
mem_resize :: proc(mem: []byte, size: int, alignment: int = DEFAULT_ALIGNMENT, no_zero: bool = false, ainfo := context.allocator, loc := #caller_location) -> ([]byte, AllocatorError) {
|
||||
assert(ainfo.procedure != nil)
|
||||
input := AllocatorProc_In {
|
||||
data = ainfo.data,
|
||||
@@ -243,11 +237,10 @@ mem_resize :: proc(mem: []byte, size: int, alignment: int = MEMORY_ALIGNMENT_DEF
|
||||
old_allocation = mem,
|
||||
loc = loc,
|
||||
}
|
||||
output: AllocatorProc_Out
|
||||
resolve_allocator_proc(ainfo.procedure)(input, & output)
|
||||
output: AllocatorProc_Out; resolve_allocator_proc(ainfo.procedure)(input, & output)
|
||||
return output.allocation, output.error
|
||||
}
|
||||
mem_shrink :: proc(mem: []byte, size: int, alignment: int = MEMORY_ALIGNMENT_DEFAULT, no_zero: bool = false, ainfo := context.allocator, loc := #caller_location) -> ([]byte, AllocatorError) {
|
||||
mem_shrink :: proc(mem: []byte, size: int, alignment: int = DEFAULT_ALIGNMENT, no_zero: bool = false, ainfo := context.allocator, loc := #caller_location) -> ([]byte, AllocatorError) {
|
||||
assert(ainfo.procedure != nil)
|
||||
input := AllocatorProc_In {
|
||||
data = ainfo.data,
|
||||
@@ -257,12 +250,11 @@ mem_shrink :: proc(mem: []byte, size: int, alignment: int = MEMORY_ALIGNMENT_DEF
|
||||
old_allocation = mem,
|
||||
loc = loc,
|
||||
}
|
||||
output: AllocatorProc_Out
|
||||
resolve_allocator_proc(ainfo.procedure)(input, & output)
|
||||
output: AllocatorProc_Out; resolve_allocator_proc(ainfo.procedure)(input, & output)
|
||||
return output.allocation, output.error
|
||||
}
|
||||
|
||||
alloc_type :: proc($Type: typeid, alignment: int = MEMORY_ALIGNMENT_DEFAULT, no_zero: bool = false, ainfo := context.allocator, loc := #caller_location) -> (^Type, AllocatorError) {
|
||||
alloc_type :: proc($Type: typeid, alignment: int = DEFAULT_ALIGNMENT, no_zero: bool = false, ainfo := context.allocator, loc := #caller_location) -> (^Type, AllocatorError) {
|
||||
assert(ainfo.procedure != nil)
|
||||
input := AllocatorProc_In {
|
||||
data = ainfo.data,
|
||||
@@ -271,11 +263,10 @@ alloc_type :: proc($Type: typeid, alignment: int = MEMORY_ALIGNMENT_DEFAULT, no
|
||||
alignment = alignment,
|
||||
loc = loc,
|
||||
}
|
||||
output: AllocatorProc_Out
|
||||
resolve_allocator_proc(ainfo.procedure)(input, & output)
|
||||
output: AllocatorProc_Out; resolve_allocator_proc(ainfo.procedure)(input, & output)
|
||||
return transmute(^Type) raw_data(output.allocation), output.error
|
||||
}
|
||||
alloc_slice :: proc($SliceType: typeid / []$Type, num: int, alignment: int = MEMORY_ALIGNMENT_DEFAULT, no_zero: bool = false, ainfo := context.allocator, loc := #caller_location) -> ([]Type, AllocatorError) {
|
||||
alloc_slice :: proc($SliceType: typeid / []$Type, num: int, alignment: int = DEFAULT_ALIGNMENT, no_zero: bool = false, ainfo := context.allocator, loc := #caller_location) -> ([]Type, AllocatorError) {
|
||||
assert(ainfo.procedure != nil)
|
||||
input := AllocatorProc_In {
|
||||
data = ainfo.data,
|
||||
@@ -284,7 +275,6 @@ alloc_slice :: proc($SliceType: typeid / []$Type, num: int, alignment: int = MEM
|
||||
alignment = alignment,
|
||||
loc = loc,
|
||||
}
|
||||
output: AllocatorProc_Out
|
||||
resolve_allocator_proc(ainfo.procedure)(input, & output)
|
||||
output: AllocatorProc_Out; resolve_allocator_proc(ainfo.procedure)(input, & output)
|
||||
return transmute([]Type) slice(raw_data(output.allocation), num), output.error
|
||||
}
|
||||
|
||||
@@ -79,7 +79,7 @@ array_set_capacity :: proc( self : ^Array( $ Type ), new_capacity: int) -> Alloc
|
||||
header_size :: size_of(ArrayHeader(Type))
|
||||
new_size := header_size + new_capacity * size_of(Type)
|
||||
old_size := header_size + self.capacity * size_of(Type)
|
||||
new_mem, result_code := mem_resize( slice(transmute(^u8)self.header, old_size), new_size, MEMORY_ALIGNMENT_DEFAULT, ainfo = self.backing )
|
||||
new_mem, result_code := mem_resize( slice(transmute(^u8)self.header, old_size), new_size, DEFAULT_ALIGNMENT, ainfo = self.backing )
|
||||
if ensure( result_code != AllocatorError.None, "Failed to allocate for new array capacity" ) {
|
||||
log_print( "Failed to allocate for new array capacity", level = LoggerLevel.Warning )
|
||||
return result_code
|
||||
|
||||
@@ -17,7 +17,7 @@ farena_init :: proc "contextless" (arena: ^FArena, backing: []byte) {
|
||||
arena.used = 0
|
||||
}
|
||||
@require_results
|
||||
farena_push :: proc "contextless" (arena: ^FArena, $Type: typeid, amount: int, alignment: int = MEMORY_ALIGNMENT_DEFAULT, loc := #caller_location) -> ([]Type, AllocatorError) {
|
||||
farena_push :: proc "contextless" (arena: ^FArena, $Type: typeid, amount: int, alignment: int = DEFAULT_ALIGNMENT, loc := #caller_location) -> ([]Type, AllocatorError) {
|
||||
assert_contextless(arena != nil)
|
||||
if amount == 0 {
|
||||
return {}, .None
|
||||
@@ -32,7 +32,7 @@ farena_push :: proc "contextless" (arena: ^FArena, $Type: typeid, amount: int, a
|
||||
return slice(cursor(arena.mem)[arena.used:], amount), .None
|
||||
}
|
||||
@require_results
|
||||
farena_grow :: proc "contextless" (arena: ^FArena, old_allocation: []byte, requested_size: int, alignment: int = MEMORY_ALIGNMENT_DEFAULT, should_zero: bool = true, loc := #caller_location) -> (allocation: []byte, err: AllocatorError) {
|
||||
farena_grow :: proc "contextless" (arena: ^FArena, old_allocation: []byte, requested_size: int, alignment: int = DEFAULT_ALIGNMENT, should_zero: bool = true, loc := #caller_location) -> (allocation: []byte, err: AllocatorError) {
|
||||
assert_contextless(arena != nil)
|
||||
if len(old_allocation) == 0 {
|
||||
return {}, .Invalid_Argument
|
||||
@@ -58,7 +58,7 @@ farena_grow :: proc "contextless" (arena: ^FArena, old_allocation: []byte, reque
|
||||
return
|
||||
}
|
||||
@require_results
|
||||
farena_shirnk :: proc "contextless" (arena: ^FArena, old_allocation: []byte, requested_size: int, alignment: int = MEMORY_ALIGNMENT_DEFAULT, loc := #caller_location) -> (allocation: []byte, err: AllocatorError) {
|
||||
farena_shirnk :: proc "contextless" (arena: ^FArena, old_allocation: []byte, requested_size: int, alignment: int = DEFAULT_ALIGNMENT, loc := #caller_location) -> (allocation: []byte, err: AllocatorError) {
|
||||
assert_contextless(arena != nil)
|
||||
if len(old_allocation) == 0 {
|
||||
return {}, .Invalid_Argument
|
||||
@@ -70,7 +70,7 @@ farena_shirnk :: proc "contextless" (arena: ^FArena, old_allocation: []byte, req
|
||||
return old_allocation[:requested_size], .None
|
||||
}
|
||||
// Calculate shrinkage
|
||||
aligned_original := align_pow2(len(old_allocation), MEMORY_ALIGNMENT_DEFAULT)
|
||||
aligned_original := align_pow2(len(old_allocation), DEFAULT_ALIGNMENT)
|
||||
aligned_new := align_pow2(requested_size, alignment)
|
||||
arena.used -= (aligned_original - aligned_new)
|
||||
return old_allocation[:requested_size], .None
|
||||
@@ -162,7 +162,7 @@ farena_odin_allocator_proc :: proc(
|
||||
info := (^Odin_AllocatorQueryInfo)(old_memory)
|
||||
info.pointer = transmute(rawptr) farena_save(arena^).slot
|
||||
info.size = len(arena.mem) - arena.used
|
||||
info.alignment = MEMORY_ALIGNMENT_DEFAULT
|
||||
info.alignment = DEFAULT_ALIGNMENT
|
||||
return to_bytes(info), nil
|
||||
}
|
||||
panic_contextless("Impossible path")
|
||||
|
||||
@@ -31,7 +31,7 @@ ktl_populate_slice_a2_str :: #force_inline proc(kt: ^[]KTL_Slot(string), backing
|
||||
raw_bytes, error := mem_alloc(size_of(KTL_Slot(string)) * len(values), ainfo = backing); assert(error == .None);
|
||||
kt^ = slice( transmute([^]KTL_Slot(string)) cursor(raw_bytes), len(raw_bytes) / size_of(KTL_Slot(string)) )
|
||||
for id in 0 ..< len(values) {
|
||||
mem_copy_non_overlapping(& kt[id].value, & values[id][1], size_of(string))
|
||||
mem_copy(& kt[id].value, & values[id][1], size_of(string))
|
||||
hash64_fnv1a(& kt[id].key, transmute([]byte) values[id][0])
|
||||
}
|
||||
}
|
||||
|
||||
@@ -11,9 +11,9 @@ import "base:intrinsics"
|
||||
// mem_copy :: intrinsics.mem_copy_non_overlapping
|
||||
// mem_copy_overlapping :: intrinsics.mem_copy
|
||||
|
||||
mem_zero :: #force_inline proc "contextless" (data: rawptr, len: int) { intrinsics.mem_zero (data, len) }
|
||||
mem_copy_non_overlapping :: #force_inline proc "contextless" (dst, src: rawptr, len: int) { intrinsics.mem_copy_non_overlapping(dst, src, len) }
|
||||
mem_copy :: #force_inline proc "contextless" (dst, src: rawptr, len: int) { intrinsics.mem_copy (dst, src, len) }
|
||||
mem_zero :: #force_inline proc "contextless" (data: rawptr, len: int) { intrinsics.mem_zero (data, len) }
|
||||
mem_copy :: #force_inline proc "contextless" (dst, src: rawptr, len: int) { intrinsics.mem_copy_non_overlapping(dst, src, len) }
|
||||
mem_copy_overlapping :: #force_inline proc "contextless" (dst, src: rawptr, len: int) { intrinsics.mem_copy (dst, src, len) }
|
||||
|
||||
import "base:runtime"
|
||||
Assertion_Failure_Proc :: runtime.Assertion_Failure_Proc
|
||||
@@ -40,6 +40,9 @@ import "core:log"
|
||||
Logger_Full_Timestamp_Opts :: log.Full_Timestamp_Opts
|
||||
|
||||
import "core:mem"
|
||||
DEFAULT_ALIGNMENT :: mem.DEFAULT_ALIGNMENT
|
||||
DEFAULT_PAGE_SIZE :: mem.DEFAULT_PAGE_SIZE
|
||||
|
||||
Odin_Allocator :: mem.Allocator
|
||||
Odin_AllocatorError :: mem.Allocator_Error
|
||||
Odin_AllocatorQueryInfo :: mem.Allocator_Query_Info
|
||||
@@ -141,8 +144,8 @@ copy :: proc {
|
||||
mem_copy,
|
||||
slice_copy,
|
||||
}
|
||||
copy_non_overlapping :: proc {
|
||||
mem_copy_non_overlapping,
|
||||
copy_overlapping :: proc {
|
||||
mem_copy_overlapping,
|
||||
slice_copy_overlapping,
|
||||
}
|
||||
fill :: proc {
|
||||
|
||||
@@ -22,7 +22,6 @@ VArenaFlags :: bit_set[VArenaFlag; u32]
|
||||
VArenaFlag :: enum u32 {
|
||||
No_Large_Pages,
|
||||
}
|
||||
|
||||
VArena :: struct {
|
||||
using vmem: VirtualMemoryRegion,
|
||||
commit_size: int,
|
||||
@@ -46,13 +45,13 @@ varena_make :: proc(to_reserve, commit_size: int, base_address: uintptr, flags:
|
||||
}
|
||||
arena = transmute(^VArena) vmem.base_address;
|
||||
arena.vmem = vmem
|
||||
arena.commit_used = align_pow2(size_of(arena), MEMORY_ALIGNMENT_DEFAULT)
|
||||
arena.commit_used = align_pow2(size_of(arena), DEFAULT_ALIGNMENT)
|
||||
arena.flags = flags
|
||||
return
|
||||
}
|
||||
varena_alloc :: proc(self: ^VArena,
|
||||
size: int,
|
||||
alignment: int = MEMORY_ALIGNMENT_DEFAULT,
|
||||
size: int,
|
||||
alignment: int = DEFAULT_ALIGNMENT,
|
||||
zero_memory := true,
|
||||
location := #caller_location
|
||||
) -> (data: []byte, alloc_error: AllocatorError)
|
||||
@@ -104,11 +103,11 @@ varena_alloc :: proc(self: ^VArena,
|
||||
}
|
||||
return
|
||||
}
|
||||
varena_grow :: #force_inline proc(self: ^VArena, old_memory: []byte, requested_size: int, alignment: int = MEMORY_ALIGNMENT_DEFAULT, should_zero := true, loc := #caller_location
|
||||
varena_grow :: #force_inline proc(self: ^VArena, old_memory: []byte, requested_size: int, alignment: int = DEFAULT_ALIGNMENT, zero_memory := true, loc := #caller_location
|
||||
) -> (data: []byte, error: AllocatorError)
|
||||
{
|
||||
if ensure(old_memory == nil, "Growing without old_memory?") {
|
||||
data, error = varena_alloc(self, requested_size, alignment, should_zero, loc)
|
||||
data, error = varena_alloc(self, requested_size, alignment, zero_memory, loc)
|
||||
return
|
||||
}
|
||||
if ensure(requested_size == len(old_memory), "Requested grow when none needed") {
|
||||
@@ -137,18 +136,18 @@ varena_grow :: #force_inline proc(self: ^VArena, old_memory: []byte, requested_s
|
||||
{
|
||||
// Give it new memory and copy the old over. Old memory is unrecoverable until clear.
|
||||
new_region : []byte
|
||||
new_region, error = varena_alloc( self, requested_size, alignment, should_zero, loc )
|
||||
new_region, error = varena_alloc( self, requested_size, alignment, zero_memory, loc )
|
||||
if ensure(new_region == nil || error != .None, "Failed to grab new region") {
|
||||
data = old_memory
|
||||
return
|
||||
}
|
||||
copy_non_overlapping( cursor(new_region), cursor(old_memory), len(old_memory) )
|
||||
copy( cursor(new_region), cursor(old_memory), len(old_memory) )
|
||||
data = new_region
|
||||
// log_print_fmt("varena resize (new): old: %p %v new: %p %v", old_memory, old_size, (& data[0]), size)
|
||||
return
|
||||
}
|
||||
new_region : []byte
|
||||
new_region, error = varena_alloc( self, requested_size - len(old_memory), alignment, should_zero, loc)
|
||||
new_region, error = varena_alloc( self, requested_size - len(old_memory), alignment, zero_memory, loc)
|
||||
if ensure(new_region == nil || error != .None, "Failed to grab new region") {
|
||||
data = old_memory
|
||||
return
|
||||
@@ -243,7 +242,7 @@ varena_odin_allocator_proc :: proc(
|
||||
info := (^Odin_AllocatorQueryInfo)(old_memory)
|
||||
info.pointer = transmute(rawptr) varena_save(arena).slot
|
||||
info.size = cast(int) arena.reserved
|
||||
info.alignment = MEMORY_ALIGNMENT_DEFAULT
|
||||
info.alignment = DEFAULT_ALIGNMENT
|
||||
return to_bytes(info), nil
|
||||
}
|
||||
return
|
||||
@@ -263,12 +262,12 @@ else {
|
||||
varena_allocator :: #force_inline proc "contextless" (arena: ^VArena) -> Odin_Allocator { return transmute(Odin_Allocator) AllocatorInfo{procedure = varena_allocator_proc, data = arena} }
|
||||
}
|
||||
|
||||
varena_push_item :: #force_inline proc(va: ^VArena, $Type: typeid, alignment: int = MEMORY_ALIGNMENT_DEFAULT, should_zero := true, location := #caller_location
|
||||
varena_push_item :: #force_inline proc(va: ^VArena, $Type: typeid, alignment: int = DEFAULT_ALIGNMENT, should_zero := true, location := #caller_location
|
||||
) -> (^Type, AllocatorError) {
|
||||
raw, error := varena_alloc(va, size_of(Type), alignment, should_zero, location)
|
||||
return transmute(^Type) cursor(raw), error
|
||||
}
|
||||
varena_push_slice :: #force_inline proc(va: ^VArena, $Type: typeid, amount: int, alignment: int = MEMORY_ALIGNMENT_DEFAULT, should_zero := true, location := #caller_location
|
||||
varena_push_slice :: #force_inline proc(va: ^VArena, $Type: typeid, amount: int, alignment: int = DEFAULT_ALIGNMENT, should_zero := true, location := #caller_location
|
||||
) -> ([]Type, AllocatorError) {
|
||||
raw, error := varena_alloc(va, size_of(Type) * amount, alignment, should_zero, location)
|
||||
return slice(transmute([^]Type) cursor(raw), len(raw) / size_of(Type)), error
|
||||
|
||||
@@ -19,13 +19,11 @@ Arena :: struct {
|
||||
}
|
||||
|
||||
arena_make :: proc(reserve_size : int = Mega * 64, commit_size : int = Mega * 64, base_addr: uintptr = 0, flags: ArenaFlags = {}) -> ^Arena {
|
||||
header_size := align_pow2(size_of(Arena), MEMORY_ALIGNMENT_DEFAULT)
|
||||
header_size := align_pow2(size_of(Arena), DEFAULT_ALIGNMENT)
|
||||
current, error := varena_make(reserve_size, commit_size, base_addr, transmute(VArenaFlags) flags)
|
||||
assert(error == .None)
|
||||
assert(current != nil)
|
||||
arena: ^Arena; arena, error = varena_push_item(current, Arena, 1)
|
||||
assert(error == .None)
|
||||
assert(arena != nil)
|
||||
arena^ = Arena {
|
||||
backing = current,
|
||||
prev = nil,
|
||||
@@ -36,7 +34,7 @@ arena_make :: proc(reserve_size : int = Mega * 64, commit_size : int = Mega * 64
|
||||
}
|
||||
return arena
|
||||
}
|
||||
arena_alloc :: proc(arena: ^Arena, size: int, alignment: int = MEMORY_ALIGNMENT_DEFAULT) -> []byte {
|
||||
arena_alloc :: proc(arena: ^Arena, size: int, alignment: int = DEFAULT_ALIGNMENT, should_zero := true) -> []byte {
|
||||
assert(arena != nil)
|
||||
active := arena.current
|
||||
size_requested := size
|
||||
@@ -53,13 +51,40 @@ arena_alloc :: proc(arena: ^Arena, size: int, alignment: int = MEMORY_ALIGNMENT_
|
||||
active = arena.current
|
||||
}
|
||||
result_ptr := transmute([^]byte) (uintptr(active) + uintptr(pos_pre))
|
||||
vresult, error := varena_alloc(active.backing, size_aligned, alignment)
|
||||
vresult, error := varena_alloc(active.backing, size_aligned, alignment, should_zero)
|
||||
assert(error == .None)
|
||||
slice_assert(vresult)
|
||||
assert(raw_data(vresult) == result_ptr)
|
||||
assert(cursor(vresult) == result_ptr)
|
||||
active.pos = pos_pst
|
||||
return slice(result_ptr, size)
|
||||
}
|
||||
arena_grow :: proc(arena: ^Arena, old_allocation: []byte, requested_size: int, alignment: int = DEFAULT_ALIGNMENT, zero_memory := true) -> (allocation: []byte) {
|
||||
active := arena.current
|
||||
if len(old_allocation) == 0 { allocation = {}; return }
|
||||
alloc_end := end(old_allocation)
|
||||
arena_end := transmute([^]byte) (uintptr(active) + uintptr(active.pos))
|
||||
if alloc_end == arena_end
|
||||
{
|
||||
// Can grow in place
|
||||
grow_amount := requested_size - len(old_allocation)
|
||||
aligned_grow := align_pow2(grow_amount, alignment)
|
||||
if active.pos + aligned_grow <= cast(int) active.backing.reserved
|
||||
{
|
||||
vresult, error := varena_alloc(active.backing, aligned_grow, alignment, zero_memory);
|
||||
assert(error == .None)
|
||||
if len(vresult) > 0 {
|
||||
active.pos += aligned_grow
|
||||
allocation = slice(cursor(old_allocation), requested_size)
|
||||
return
|
||||
}
|
||||
}
|
||||
}
|
||||
// Can't grow in place, allocate new
|
||||
allocation = arena_alloc(arena, requested_size, alignment, false)
|
||||
if len(allocation) == 0 { allocation = {}; return }
|
||||
copy(allocation, old_allocation)
|
||||
zero(cursor(allocation)[len(old_allocation):], (requested_size - len(old_allocation)) * int(zero_memory))
|
||||
return
|
||||
}
|
||||
arena_release :: proc(arena: ^Arena) {
|
||||
assert(arena != nil)
|
||||
curr := arena.current
|
||||
@@ -75,7 +100,7 @@ arena_reset :: proc(arena: ^Arena) {
|
||||
arena_rewind :: proc(arena: ^Arena, save_point: AllocatorSP) {
|
||||
assert(arena != nil)
|
||||
assert(save_point.type_sig == arena_allocator_proc)
|
||||
header_size := align_pow2(size_of(Arena), MEMORY_ALIGNMENT_DEFAULT)
|
||||
header_size := align_pow2(size_of(Arena), DEFAULT_ALIGNMENT)
|
||||
curr := arena.current
|
||||
big_pos := max(header_size, save_point.slot)
|
||||
// Release arenas that are beyond the save point
|
||||
@@ -85,8 +110,7 @@ arena_rewind :: proc(arena: ^Arena, save_point: AllocatorSP) {
|
||||
curr = prev
|
||||
}
|
||||
arena.current = curr
|
||||
new_pos := big_pos - curr.base_pos
|
||||
assert(new_pos <= curr.pos)
|
||||
new_pos := big_pos - curr.base_pos; assert(new_pos <= curr.pos)
|
||||
curr.pos = new_pos
|
||||
varena_rewind(curr.backing, { type_sig = varena_allocator_proc, slot = curr.pos + size_of(VArena) })
|
||||
}
|
||||
|
||||
@@ -32,7 +32,7 @@ virtual_reserve_remaining :: proc "contextless" ( using vmem : VirtualMemoryRegi
|
||||
@(require_results)
|
||||
virtual_commit :: proc "contextless" ( using vmem : VirtualMemoryRegion, size : uint ) -> ( alloc_error : AllocatorError )
|
||||
{
|
||||
if size < committed {
|
||||
if size < committed {
|
||||
return .None
|
||||
}
|
||||
|
||||
|
||||
@@ -24,5 +24,3 @@ pool_make :: proc() -> (pool: VPool, error: AllocatorError)
|
||||
panic("not implemented")
|
||||
// return
|
||||
}
|
||||
|
||||
|
||||
|
||||
Reference in New Issue
Block a user