-
Notifications
You must be signed in to change notification settings - Fork 4
/
mem.jou
38 lines (33 loc) · 1.69 KB
/
mem.jou
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
# Memory management
# Heap allocations
# TODO: write a tutorial about using these and add a link
declare malloc(size: long) -> void* # allocate memory
declare calloc(a: long, b: long) -> void* # allocate a*b bytes of memory and zero it
declare realloc(ptr: void*, new_size: long) -> void* # grow/shrink allocated memory
declare free(ptr: void*) -> None # release allocated memory so it can be reused
# This function fills a memory region with the given byte.
# The most common way use case for this function is zeroing memory:
#
# memset(&foo, 0, sizeof(foo))
#
declare memset(dest: void*, fill_byte: int, size: long) -> void*
# These functions copy memory from one place to another. Source and destination
# are of the same size, and pointers to their start are given.
#
# The difference between these two is how they handle overlapping memory. If
# source and destination may overlap, use memmove(). If you know that source
# and destination will never overlap, use memcpy(), because
# - it is a hint to people reading the code that there will be no overlap
# - it may be slightly faster.
declare memcpy(dest: void*, source: void*, size: long) -> void* # copy memory, overlaps are UB
declare memmove(dest: void*, source: void*, size: long) -> void* # copy memory, overlaps are ok
# Swaps the contents of two memory regions of the same size.
# This does nothing if the same memory region is passed twice.
# This probably doesn't do what you want if the memory regions overlap in some other way.
def memswap(a: void*, b: void*, size: long) -> None:
a_bytes: byte* = a
b_bytes: byte* = b
for i = 0L; i < size; i++:
old_a = a_bytes[i]
a_bytes[i] = b_bytes[i]
b_bytes[i] = old_a