amath  1.8.5
Simple command line calculator
mem.c File Reference
#include "amathc.h"
#include <stdlib.h>
Include dependency graph for mem.c:

Go to the source code of this file.

Classes

struct  MemoryBlock
 Block of allocated memory. More...
 
struct  MemoryList
 List of allocated memory. Uses the LIFO principle. More...
 

Macros

#define ALLOC_MEM(x)   calloc(1L,x)
 
#define FREE_MEM(x)   free(x)
 
#define Debug(x, y, z)
 

Functions

void alloc_error (char *descr, size_t size)
 Log a memory allocation error. More...
 
void dealloc_error (char *descr, void *p)
 Log a memory deallocation error. More...
 
void * AllocMemSafe (size_t size)
 Allocate memory and add it to the global memory list. More...
 
void RemoveMemSafe (void *block, bool deallocate)
 
void FreeMemSafe (void *block)
 Deallocate memory from the global memory list. More...
 
void DetachMemSafe (void *block)
 Detach an allocated memory from the global memory list. More...
 
void FreeAllSafe ()
 Deallocate all memory in the global memory list. More...
 
void MemUsage (long *blocks, long *size, long *peak)
 Get memory usage in the global memory list. More...
 

Variables

struct MemoryListlist = nullptr
 Global list of allocated memory. More...
 

Macro Definition Documentation

◆ ALLOC_MEM

#define ALLOC_MEM (   x)    calloc(1L,x)

Definition at line 43 of file mem.c.

◆ Debug

#define Debug (   x,
  y,
 
)

Definition at line 45 of file mem.c.

◆ FREE_MEM

#define FREE_MEM (   x)    free(x)

Definition at line 44 of file mem.c.

Function Documentation

◆ alloc_error()

void alloc_error ( char *  descr,
size_t  size 
)

Log a memory allocation error.

Definition at line 252 of file mem.c.

Referenced by AllocMemSafe().

253 {
254  Debug("Memory allocation error (%s) with size (%d)\n", descr, size);
255  //if (size == 0)
256  // exit(10);
257 }
#define Debug(x, y, z)
Definition: mem.c:45
size_t size
Definition: mem.c:60
Here is the caller graph for this function:

◆ AllocMemSafe()

void* AllocMemSafe ( size_t  size)

Allocate memory and add it to the global memory list.

Definition at line 86 of file mem.c.

References MemoryBlock::address, alloc_error(), MemoryList::count, MemoryList::first, list, MemoryBlock::next, MemoryList::peak, MemoryBlock::size, and MemoryList::size.

87 {
88  struct MemoryBlock* newblock;
89  size_t allocsize;
90 
91  if (list == nullptr)
92  {
93  list = (struct MemoryList*)ALLOC_MEM(sizeof(struct MemoryList));
94  if (!list)
95  {
96  alloc_error("list", sizeof(struct MemoryList));
97  return 0;
98  }
99 
100  list->first = nullptr;
101  list->peak = 0;
102  list->size = 0;
103  list->count = 0;
104  }
105 
106 #ifdef P64BIT
107  // Align to bytes of 8
108  allocsize = (size + 7) & ~0x07;
109 #else
110  // Align to bytes of 4
111  allocsize = (size + 3) & ~0x03;
112 #endif
113 
114  newblock = (struct MemoryBlock*)ALLOC_MEM(sizeof(struct MemoryBlock));
115  if (!newblock)
116  {
117  alloc_error("block", sizeof(struct MemoryBlock));
118  return 0;
119  }
120 
121  newblock->address = (struct MemoryBlock*)ALLOC_MEM(allocsize);
122  if (!newblock->address)
123  {
124  FREE_MEM(newblock);
125  alloc_error("memory", allocsize);
126  return 0;
127  }
128 
129  newblock->size = allocsize;
130  newblock->next = list->first;
131  list->first = newblock;
132  list->size += allocsize;
133  list->count++;
134 
135  if (list->size > list->peak)
136  {
137  list->peak = list->size;
138  }
139 
140  // Memory allocated
141  return newblock->address;
142 }
struct MemoryBlock * first
Definition: mem.c:69
size_t peak
Definition: mem.c:70
long count
Definition: mem.c:72
void alloc_error(char *, size_t)
Log a memory allocation error.
Definition: mem.c:252
size_t size
Definition: mem.c:71
struct MemoryBlock * next
Definition: mem.c:59
Block of allocated memory.
Definition: mem.c:57
void * address
Definition: mem.c:61
#define ALLOC_MEM(x)
Definition: mem.c:43
struct MemoryList * list
Global list of allocated memory.
Definition: mem.c:78
size_t size
Definition: mem.c:60
#define FREE_MEM(x)
Definition: mem.c:44
List of allocated memory. Uses the LIFO principle.
Definition: mem.c:67
Here is the call graph for this function:

◆ dealloc_error()

void dealloc_error ( char *  descr,
void *  p 
)

Log a memory deallocation error.

Definition at line 262 of file mem.c.

Referenced by RemoveMemSafe().

263 {
264  Debug("Memory deallocation error (%s) address (%x)\n", descr, p);
265 }
#define Debug(x, y, z)
Definition: mem.c:45
Here is the caller graph for this function:

◆ DetachMemSafe()

void DetachMemSafe ( void *  block)

Detach an allocated memory from the global memory list.

The memory block is only detached, not deallocated.

Definition at line 209 of file mem.c.

References RemoveMemSafe().

210 {
211  RemoveMemSafe(block, false);
212 }
void RemoveMemSafe(void *block, bool deallocate)
Definition: mem.c:144
Here is the call graph for this function:

◆ FreeAllSafe()

void FreeAllSafe ( )

Deallocate all memory in the global memory list.

Definition at line 217 of file mem.c.

References MemoryBlock::address, MemoryList::first, list, and MemoryBlock::next.

Referenced by main().

218 {
219  struct MemoryBlock *current, *next;
220 
221  if (list == nullptr)
222  {
223  return;
224  }
225 
226  current = list->first;
227  while (current != nullptr)
228  {
229  next = current->next;
230  FREE_MEM(current->address);
231  FREE_MEM(current);
232  current = next;
233  }
234 
235  FREE_MEM(list);
236  list = nullptr;
237 }
struct MemoryBlock * first
Definition: mem.c:69
struct MemoryBlock * next
Definition: mem.c:59
Block of allocated memory.
Definition: mem.c:57
void * address
Definition: mem.c:61
struct MemoryList * list
Global list of allocated memory.
Definition: mem.c:78
#define FREE_MEM(x)
Definition: mem.c:44
Here is the caller graph for this function:

◆ FreeMemSafe()

void FreeMemSafe ( void *  block)

Deallocate memory from the global memory list.

Definition at line 200 of file mem.c.

References RemoveMemSafe().

201 {
202  RemoveMemSafe(block, true);
203 }
void RemoveMemSafe(void *block, bool deallocate)
Definition: mem.c:144
Here is the call graph for this function:

◆ MemUsage()

void MemUsage ( long *  blocks,
long *  size,
long *  peak 
)

Get memory usage in the global memory list.

Definition at line 242 of file mem.c.

References MemoryList::count, list, MemoryList::peak, and MemoryList::size.

Referenced by MemoryStatement::Execute().

243 {
244  *blocks = list->count;
245  *size = (long)list->size;
246  *peak = (long)list->peak;;
247 }
size_t peak
Definition: mem.c:70
long count
Definition: mem.c:72
size_t size
Definition: mem.c:71
struct MemoryList * list
Global list of allocated memory.
Definition: mem.c:78
size_t size
Definition: mem.c:60
Here is the caller graph for this function:

◆ RemoveMemSafe()

void RemoveMemSafe ( void *  block,
bool  deallocate 
)

Definition at line 144 of file mem.c.

References MemoryBlock::address, MemoryList::count, dealloc_error(), MemoryList::first, list, MemoryBlock::next, MemoryBlock::size, and MemoryList::size.

Referenced by DetachMemSafe(), and FreeMemSafe().

145 {
146  struct MemoryBlock *current, *previous;
147 
148  if (list == nullptr || block == nullptr)
149  {
150  dealloc_error("list", 0);
151  return;
152  }
153 
154  if (block == nullptr)
155  {
156  dealloc_error("memory", 0);
157  return;
158  }
159 
160  previous = nullptr;
161  current = list->first;
162  while (current != nullptr && current->address != block)
163  {
164  previous = current;
165  current = current->next;
166  }
167 
168  if (current == nullptr)
169  {
170  dealloc_error("address not found", block);
171  return;
172  }
173 
174  if (previous == nullptr)
175  {
176  list->first = current->next;
177  }
178  else
179  {
180  previous->next = current->next;
181  }
182 
183  list->size -= current->size;
184  list->count--;
185 
186  if (deallocate)
187  {
188  FREE_MEM(current->address);
189  }
190 
191  current->address = nullptr;
192  current->next = nullptr;
193  current->size = 0;
194  FREE_MEM(current);
195 }
struct MemoryBlock * first
Definition: mem.c:69
long count
Definition: mem.c:72
size_t size
Definition: mem.c:71
struct MemoryBlock * next
Definition: mem.c:59
Block of allocated memory.
Definition: mem.c:57
void * address
Definition: mem.c:61
struct MemoryList * list
Global list of allocated memory.
Definition: mem.c:78
size_t size
Definition: mem.c:60
void dealloc_error(char *, void *)
Log a memory deallocation error.
Definition: mem.c:262
#define FREE_MEM(x)
Definition: mem.c:44
Here is the call graph for this function:
Here is the caller graph for this function:

Variable Documentation

◆ list

struct MemoryList* list = nullptr

Global list of allocated memory.

Definition at line 78 of file mem.c.

Referenced by AllocMemSafe(), FreeAllSafe(), MemUsage(), and RemoveMemSafe().