[822] | 1 | // Copyright 2021 The Libc Authors. All rights reserved.
|
---|
| 2 | // Use of this source code is governed by a BSD-style
|
---|
| 3 | // license that can be found in the LICENSE file.
|
---|
| 4 |
|
---|
| 5 | //go:build !libc.membrk && !libc.memgrind
|
---|
| 6 | // +build !libc.membrk,!libc.memgrind
|
---|
| 7 |
|
---|
| 8 | package libc // import "modernc.org/libc"
|
---|
| 9 |
|
---|
| 10 | import (
|
---|
| 11 | "modernc.org/libc/errno"
|
---|
| 12 | "modernc.org/libc/sys/types"
|
---|
| 13 | "modernc.org/memory"
|
---|
| 14 | )
|
---|
| 15 |
|
---|
| 16 | const memgrind = false
|
---|
| 17 |
|
---|
| 18 | var (
|
---|
| 19 | allocator memory.Allocator
|
---|
| 20 | )
|
---|
| 21 |
|
---|
| 22 | // void *malloc(size_t size);
|
---|
| 23 | func Xmalloc(t *TLS, n types.Size_t) uintptr {
|
---|
| 24 | if n == 0 {
|
---|
| 25 | return 0
|
---|
| 26 | }
|
---|
| 27 |
|
---|
| 28 | allocMu.Lock()
|
---|
| 29 |
|
---|
| 30 | defer allocMu.Unlock()
|
---|
| 31 |
|
---|
| 32 | p, err := allocator.UintptrMalloc(int(n))
|
---|
| 33 | if err != nil {
|
---|
| 34 | t.setErrno(errno.ENOMEM)
|
---|
| 35 | return 0
|
---|
| 36 | }
|
---|
| 37 |
|
---|
| 38 | return p
|
---|
| 39 | }
|
---|
| 40 |
|
---|
| 41 | // void *calloc(size_t nmemb, size_t size);
|
---|
| 42 | func Xcalloc(t *TLS, n, size types.Size_t) uintptr {
|
---|
| 43 | rq := int(n * size)
|
---|
| 44 | if rq == 0 {
|
---|
| 45 | return 0
|
---|
| 46 | }
|
---|
| 47 |
|
---|
| 48 | allocMu.Lock()
|
---|
| 49 |
|
---|
| 50 | defer allocMu.Unlock()
|
---|
| 51 |
|
---|
| 52 | p, err := allocator.UintptrCalloc(int(n * size))
|
---|
| 53 | if err != nil {
|
---|
| 54 | t.setErrno(errno.ENOMEM)
|
---|
| 55 | return 0
|
---|
| 56 | }
|
---|
| 57 |
|
---|
| 58 | return p
|
---|
| 59 | }
|
---|
| 60 |
|
---|
| 61 | // void *realloc(void *ptr, size_t size);
|
---|
| 62 | func Xrealloc(t *TLS, ptr uintptr, size types.Size_t) uintptr {
|
---|
| 63 | allocMu.Lock()
|
---|
| 64 |
|
---|
| 65 | defer allocMu.Unlock()
|
---|
| 66 |
|
---|
| 67 | p, err := allocator.UintptrRealloc(ptr, int(size))
|
---|
| 68 | if err != nil {
|
---|
| 69 | t.setErrno(errno.ENOMEM)
|
---|
| 70 | return 0
|
---|
| 71 | }
|
---|
| 72 |
|
---|
| 73 | return p
|
---|
| 74 | }
|
---|
| 75 |
|
---|
| 76 | // void free(void *ptr);
|
---|
| 77 | func Xfree(t *TLS, p uintptr) {
|
---|
| 78 | if p == 0 {
|
---|
| 79 | return
|
---|
| 80 | }
|
---|
| 81 |
|
---|
| 82 | allocMu.Lock()
|
---|
| 83 |
|
---|
| 84 | defer allocMu.Unlock()
|
---|
| 85 |
|
---|
| 86 | allocator.UintptrFree(p)
|
---|
| 87 | }
|
---|
| 88 |
|
---|
| 89 | func UsableSize(p uintptr) types.Size_t {
|
---|
| 90 | allocMu.Lock()
|
---|
| 91 |
|
---|
| 92 | defer allocMu.Unlock()
|
---|
| 93 |
|
---|
| 94 | return types.Size_t(memory.UintptrUsableSize(p))
|
---|
| 95 | }
|
---|
| 96 |
|
---|
| 97 | // MemAuditStart locks the memory allocator, initializes and enables memory
|
---|
| 98 | // auditing. Finaly it unlocks the memory allocator.
|
---|
| 99 | //
|
---|
| 100 | // Some memory handling errors, like double free or freeing of unallocated
|
---|
| 101 | // memory, will panic when memory auditing is enabled.
|
---|
| 102 | //
|
---|
| 103 | // This memory auditing functionality has to be enabled using the libc.memgrind
|
---|
| 104 | // build tag.
|
---|
| 105 | //
|
---|
| 106 | // It is intended only for debug/test builds. It slows down memory allocation
|
---|
| 107 | // routines and it has additional memory costs.
|
---|
| 108 | func MemAuditStart() {}
|
---|
| 109 |
|
---|
| 110 | // MemAuditReport locks the memory allocator, reports memory leaks, if any.
|
---|
| 111 | // Finally it disables memory auditing and unlocks the memory allocator.
|
---|
| 112 | //
|
---|
| 113 | // This memory auditing functionality has to be enabled using the libc.memgrind
|
---|
| 114 | // build tag.
|
---|
| 115 | //
|
---|
| 116 | // It is intended only for debug/test builds. It slows down memory allocation
|
---|
| 117 | // routines and it has additional memory costs.
|
---|
| 118 | func MemAuditReport() error { return nil }
|
---|