1 #include "ltfat.h"
2 #include "ltfat/types.h"
3 #include "ltfat/memalloc.h"
4
5 #ifdef FFTW
6 #include "ltfat/thirdparty/fftw3.h"
7 #endif
8
9 #include <stdlib.h>
10 /* #include "ltfat/macros.h" */
11
12
13 void* (*ltfat_custom_malloc)(size_t) = NULL;
14 void (*ltfat_custom_free)(void*) = NULL;
15
16 ltfat_memory_handler_t
ltfat_set_memory_handler(ltfat_memory_handler_t new_handler)17 ltfat_set_memory_handler (ltfat_memory_handler_t new_handler)
18 {
19 ltfat_memory_handler_t retVal = { ltfat_custom_malloc, ltfat_custom_free };
20
21 ltfat_custom_malloc = new_handler.malloc;
22 ltfat_custom_free = new_handler.free;
23 return retVal;
24 }
25
26 #ifdef KISS
27 #define ALIGNBOUNDARY 64
28
29 static void*
ltfat_aligned_malloc(size_t size)30 ltfat_aligned_malloc(size_t size)
31 {
32 void* mem = malloc(size + sizeof(void*) + ALIGNBOUNDARY - 1);
33 void* ptr = (void**)
34 (((size_t)mem + (ALIGNBOUNDARY - 1) + sizeof(void*)) &
35 ~(ALIGNBOUNDARY - 1));
36
37 ((void**) ptr)[-1] = mem;
38 return ptr;
39 }
40
41 static void
ltfat_aligned_free(void * ptr)42 ltfat_aligned_free(void* ptr)
43 {
44 free(((void**) ptr)[-1]);
45 }
46 #endif
47
48 LTFAT_API void*
ltfat_malloc(size_t n)49 ltfat_malloc (size_t n)
50 {
51 void* outp;
52
53 if (ltfat_custom_malloc)
54 outp = (*ltfat_custom_malloc)(n);
55 else
56 #ifdef FFTW
57 outp = LTFAT_FFTW(malloc)(n);
58 #elif KISS
59 outp = ltfat_aligned_malloc(n);
60 #else
61 #error "No FFT backend specified. Use -DKISS or -DFFTW"
62 #endif
63 return outp;
64 }
65
66
67 LTFAT_API void*
ltfat_postpad(void * ptr,size_t nold,size_t nnew)68 ltfat_postpad (void* ptr, size_t nold, size_t nnew)
69 {
70 if(!ptr)
71 return ltfat_calloc(nnew, 1);
72
73 if (nnew > nold)
74 {
75 void* outp = ltfat_realloc (ptr, nold, nnew);
76 if (!outp) return NULL;
77
78 memset(((unsigned char*)outp) + nold, 0, nnew - nold);
79 return outp;
80 }
81 return ptr;
82 }
83
84 LTFAT_API void*
ltfat_realloc(void * ptr,size_t nold,size_t nnew)85 ltfat_realloc (void* ptr, size_t nold, size_t nnew)
86 {
87 void* outp = ltfat_malloc(nnew);
88
89 if (!outp) return NULL;
90
91 if (ptr)
92 {
93 memcpy(outp, ptr, nold < nnew ? nold : nnew);
94 ltfat_free(ptr);
95 }
96
97 return outp;
98 }
99
100 LTFAT_API void*
ltfat_calloc(size_t nmemb,size_t size)101 ltfat_calloc (size_t nmemb, size_t size)
102 {
103 void* outp = ltfat_malloc(nmemb * size);
104
105 if (!outp)
106 return NULL;
107
108 memset(outp, 0, nmemb * size);
109
110 return outp;
111 }
112
113 LTFAT_API void
ltfat_free(const void * ptr)114 ltfat_free(const void* ptr)
115 {
116 if (ltfat_custom_free)
117 (*ltfat_custom_free)((void*)ptr);
118 else
119 #ifdef FFTW
120 LTFAT_FFTW(free)((void*)ptr);
121 #elif KISS
122 ltfat_aligned_free((void*)ptr);
123 #endif
124 }
125
126 LTFAT_API void
ltfat_safefree(const void * ptr)127 ltfat_safefree(const void* ptr)
128 {
129 if (ptr)
130 ltfat_free((void*)ptr);
131 }
132