source: trunk/src/sh_mem.c@ 1

Last change on this file since 1 was 1, checked in by katerina, 19 years ago

Initial import

File size: 11.1 KB
RevLine 
[1]1/* SAMHAIN file system integrity testing */
2/* Copyright (C) 1999, 2000 Rainer Wichmann */
3/* */
4/* This program is free software; you can redistribute it */
5/* and/or modify */
6/* it under the terms of the GNU General Public License as */
7/* published by */
8/* the Free Software Foundation; either version 2 of the License, or */
9/* (at your option) any later version. */
10/* */
11/* This program is distributed in the hope that it will be useful, */
12/* but WITHOUT ANY WARRANTY; without even the implied warranty of */
13/* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the */
14/* GNU General Public License for more details. */
15/* */
16/* You should have received a copy of the GNU General Public License */
17/* along with this program; if not, write to the Free Software */
18/* Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. */
19
20#include "config_xor.h"
21
22
23#include <stdio.h>
24#include <stdlib.h>
25#include <string.h>
26#include <sys/types.h>
27#include <unistd.h>
28
29
30#ifdef HAVE_MEMORY_H
31#include <memory.h>
32#endif
33
34#include "samhain.h"
35#include "sh_error.h"
36#include "sh_utils.h"
37#include "sh_mem.h"
38
39extern int safe_logger (int signal, int method, pid_t thepid);
40
41#undef FIL__
42#define FIL__ _("sh_mem.c")
43static int eblock = 0;
44
45#ifdef MEM_DEBUG
46
47#define CHECKBYTE 0x7F
48
49/* Memory alignment; should be 16 bytes on 64 bit machines.
50 * -> 32 bytes overhead/allocation
51 */
52#define SH_MEMMULT 16
53
54
55typedef struct mem_struct {
56 struct mem_struct *next; /* link to next struct */
57 char * real_address; /* address assigned */
58 char * address; /* address returned */
59 unsigned long size; /* size allocated */
60 char file[20]; /* Allocation file name */
61 int line; /* Allocation line number */
62} memlist_t;
63
64memlist_t * memlist = NULL;
65
66int Free_Count = 0, Alloc_Count = 0;
67int Now_Alloc_Count = 0, Max_Alloc_Count = 0;
68unsigned long Mem_Current = 0, Mem_Max = 0;
69
70#if 0
71#define MEM_DETAILS
72#endif
73
74#ifdef MEM_DETAILS
75int max_upto_032 = 0;
76int max_upto_064 = 0;
77int max_upto_128 = 0;
78int max_upto_256 = 0;
79int max_upto_512 = 0;
80int max_upto_1024 = 0;
81int max_upto_4096 = 0;
82int max_upto_inf = 0;
83
84int now_upto_032 = 0;
85int now_upto_064 = 0;
86int now_upto_128 = 0;
87int now_upto_256 = 0;
88int now_upto_512 = 0;
89int now_upto_1024 = 0;
90int now_upto_4096 = 0;
91int now_upto_inf = 0;
92
93int tot_upto_032 = 0;
94int tot_upto_064 = 0;
95int tot_upto_128 = 0;
96int tot_upto_256 = 0;
97int tot_upto_512 = 0;
98int tot_upto_1024 = 0;
99int tot_upto_4096 = 0;
100int tot_upto_inf = 0;
101#endif
102
103#ifdef MEM_LOG
104void sh_mem_dump ()
105{
106 memlist_t * this = memlist;
107
108
109 FILE * fd = fopen(MEM_LOG, "w");
110
111 while (this != NULL)
112 {
113 fprintf (fd, "%20s %5d %ld\n", this->file, this->line, this->size);
114 this = this->next;
115 }
116 fclose(fd);
117 return;
118}
119#else
120void sh_mem_dump ()
121{
122 return;
123}
124#endif
125
126void sh_mem_stat ()
127{
128 memlist_t * this;
129
130
131 SL_ENTER(_("sh_mem_stat"));
132
133 if (Alloc_Count == Free_Count)
134 {
135 sh_error_handle ((-1), FIL__, __LINE__, 0, MSG_MSTAMP,
136 Mem_Max, Mem_Current);
137 SL_RET0(_("sh_mem_stat"));
138 }
139
140 sh_error_handle (SH_ERR_INFO, FIL__, __LINE__, 0, MSG_MSTAMP2,
141 Alloc_Count, Free_Count, Max_Alloc_Count);
142 sh_error_handle (SH_ERR_INFO, FIL__, __LINE__, 0, MSG_MSTAMP,
143 Mem_Max, Mem_Current);
144
145#ifdef MEM_DETAILS
146 fprintf(stderr, "\n");
147 fprintf(stderr, "__SIZE_____TOTAL___MAXIMUM___\n");
148 fprintf(stderr, " 32 %6d %6d\n", tot_upto_032, max_upto_032);
149 fprintf(stderr, " 64 %6d %6d\n", tot_upto_064, max_upto_064);
150 fprintf(stderr, " 128 %6d %6d\n", tot_upto_128, max_upto_128);
151 fprintf(stderr, " 256 %6d %6d\n", tot_upto_256, max_upto_256);
152 fprintf(stderr, " 512 %6d %6d\n", tot_upto_512, max_upto_512);
153 fprintf(stderr, " 1024 %6d %6d\n", tot_upto_1024, max_upto_1024);
154 fprintf(stderr, " 4096 %6d %6d\n", tot_upto_4096, max_upto_4096);
155 fprintf(stderr, " inf %6d %6d\n", tot_upto_inf, max_upto_inf);
156 fprintf(stderr, "\n");
157#endif
158
159 this = memlist;
160
161 while (this != NULL)
162 {
163 sh_error_handle (SH_ERR_WARN, FIL__, __LINE__, 0, MSG_E_NOTFREE,
164 this->size, this->file, this->line);
165 this = this->next;
166 }
167
168 SL_RET0(_("sh_mem_stat"));
169}
170
171void sh_mem_check ()
172{
173 memlist_t * this;
174 long nerr = 0;
175
176 SL_ENTER(_("sh_mem_check"));
177
178 sh_error_handle ((-1), FIL__, __LINE__, 0, MSG_MSTAMP,
179 Mem_Max, Mem_Current);
180
181 this = memlist;
182
183 while (this != NULL)
184 {
185 if ( this->address == NULL )
186 {
187 sh_error_handle ((-1), FIL__, __LINE__, 0, MSG_E_MNULL);
188 ++nerr;
189 }
190 else
191 {
192 if ( this->address[this->size] != CHECKBYTE )
193 {
194 sh_error_handle ((-1), FIL__, __LINE__, 0, MSG_E_MOVER,
195 this->file, this->line, FIL__, __LINE__);
196 ++nerr;
197 }
198 if ( this->real_address[SH_MEMMULT-1] != CHECKBYTE )
199 {
200 sh_error_handle ((-1), FIL__, __LINE__, 0, MSG_E_MUNDER,
201 this->file, this->line, FIL__, __LINE__);
202 ++nerr;
203 }
204 }
205 this = this->next;
206 }
207
208 /* if (nerr > 0) abort(); */
209
210 SL_RET0(_("sh_mem_check"));
211}
212
213void * sh_mem_malloc (size_t size, char * file, int line)
214{
215 void * the_realAddress;
216 void * theAddress;
217 memlist_t * this;
218
219 SL_ENTER(_("sh_mem_malloc"));
220
221 the_realAddress = malloc(size + 2 * SH_MEMMULT);
222
223 if ( the_realAddress == NULL )
224 {
225 if (eblock == 0)
226 {
227 eblock = 1;
228 (void) safe_logger (0, 0, getpid());
229 /*
230 sh_error_handle ((-1), FIL__, __LINE__, 0, MSG_E_MMEM,
231 file, line);
232 */
233 eblock = 0;
234 }
235 /* use _exit() rather than exit() - we malloc() in atexit() functions
236 */
237 _exit (42);
238 }
239
240 /* --- Set check bytes. ---
241 */
242 theAddress = ((char *) the_realAddress + SH_MEMMULT);
243
244 memset(the_realAddress, CHECKBYTE, SH_MEMMULT);
245 memset(theAddress, CHECKBYTE, size + 1);
246 memset(theAddress, 0, 1);
247
248 ++Alloc_Count;
249 ++Now_Alloc_Count;
250
251 if (Max_Alloc_Count < Now_Alloc_Count)
252 Max_Alloc_Count = Now_Alloc_Count;
253
254#ifdef MEM_DETAILS
255 if (size <= 32)
256 {
257 ++now_upto_032;
258 ++tot_upto_032;
259 if (now_upto_032 > max_upto_032) max_upto_032 = now_upto_032;
260 }
261 else if (size <= 64)
262 {
263 ++now_upto_064;
264 ++tot_upto_064;
265 if (now_upto_064 > max_upto_064) max_upto_064 = now_upto_064;
266 }
267 else if (size <= 128)
268 {
269 ++now_upto_128;
270 ++tot_upto_128;
271 if (now_upto_128 > max_upto_128) max_upto_128 = now_upto_128;
272 }
273 else if (size <= 256)
274 {
275 ++now_upto_256;
276 ++tot_upto_256;
277 if (now_upto_256 > max_upto_256) max_upto_256 = now_upto_256;
278 }
279 else if (size <= 512)
280 {
281 ++now_upto_512;
282 ++tot_upto_512;
283 if (now_upto_512 > max_upto_512) max_upto_512 = now_upto_512;
284 }
285 else if (size <= 1024)
286 {
287 ++now_upto_1024;
288 ++tot_upto_1024;
289 if (now_upto_1024 > max_upto_1024) max_upto_1024 = now_upto_1024;
290 }
291 else if (size <= 4096)
292 {
293 ++now_upto_4096;
294 ++tot_upto_4096;
295 if (now_upto_4096 > max_upto_4096) max_upto_4096 = now_upto_4096;
296 }
297 else
298 {
299 ++now_upto_inf;
300 ++tot_upto_inf;
301 if (now_upto_inf > max_upto_inf) max_upto_inf = now_upto_inf;
302
303 fprintf(stderr, "\n___BIGSIZE___");
304 fprintf(stderr, " %6d -> %16s %10d \n", size, file, line);
305 fprintf(stderr, "\n");
306
307 }
308#endif
309
310 Mem_Current += size;
311 Mem_Max = ( (Mem_Current > Mem_Max) ? Mem_Current : Mem_Max);
312
313 this = (memlist_t *) malloc (sizeof(memlist_t));
314
315 if ( this == NULL)
316 {
317 if (eblock == 0)
318 {
319 eblock = 1;
320 (void) safe_logger(0, 0, getpid());
321 /*
322 sh_error_handle ((-1), FIL__, __LINE__, 0, MSG_E_MMEM,
323 file, line);
324 */
325 eblock = 0;
326 }
327 SL_RETURN( the_realAddress, _("sh_mem_malloc"));
328 }
329
330 /* make list entry */
331
332 this->real_address = the_realAddress;
333 this->address = theAddress;
334 this->size = size;
335 this->line = line;
336 sl_strlcpy(this->file, file, 20);
337
338 this->next = memlist;
339 memlist = this;
340
341 SL_RETURN( theAddress, _("sh_mem_malloc"));
342}
343
344
345void sh_mem_free (void * a, char * file, int line)
346{
347 memlist_t * this = memlist;
348 memlist_t * before = memlist;
349 unsigned long size = 0;
350
351 SL_ENTER(_("sh_mem_free"));
352
353 if ( a == NULL )
354 {
355 sh_error_handle ((-1), FIL__, __LINE__, 0, MSG_E_MNULL,
356 file, line);
357 SL_RET0(_("sh_mem_free"));
358 }
359
360 /* -- Find record. --
361 */
362 while (this != NULL)
363 {
364 if (this->address == a)
365 break;
366 before = this;
367 this = this->next;
368 }
369
370 if (this == NULL)
371 {
372 sh_error_handle ((-1), FIL__, __LINE__, 0, MSG_E_MREC,
373 file, line);
374 SL_RET0(_("sh_mem_free"));
375 }
376 else
377 {
378 a = this->real_address;
379
380 if ( this->address[this->size] != CHECKBYTE )
381 {
382 sh_error_handle ((-1), FIL__, __LINE__, 0, MSG_E_MOVER,
383 this->file, this->line, file, line);
384 }
385 if ( this->real_address[SH_MEMMULT-1] != CHECKBYTE )
386 sh_error_handle ((-1), FIL__, __LINE__, 0, MSG_E_MUNDER,
387 this->file, this->line, file, line);
388
389 size = this->size;
390
391 if (this == memlist)
392 memlist = this->next;
393 else
394 before->next = this->next;
395 }
396
397 free(a);
398 if (this)
399 free(this);
400 ++Free_Count;
401 --Now_Alloc_Count;
402
403#ifdef MEM_DETAILS
404 if (size <= 32)
405 --now_upto_032;
406 else if (size <= 64)
407 --now_upto_064;
408 else if (size <= 128)
409 --now_upto_128;
410 else if (size <= 256)
411 --now_upto_256;
412 else if (size <= 512)
413 --now_upto_512;
414 else if (size <= 1024)
415 --now_upto_1024;
416 else if (size <= 4096)
417 --now_upto_4096;
418 else
419 --now_upto_inf;
420#endif
421
422 Mem_Current -= size;
423 SL_RET0(_("sh_mem_free"));
424}
425
426#else
427
428void sh_mem_free (void * a)
429{
430 SL_ENTER(_("sh_mem_free"));
431
432 if (a)
433 {
434 free(a);
435 }
436 else
437 {
438 sh_error_handle ((-1), FIL__, __LINE__, 0, MSG_E_MNULL);
439 }
440 SL_RET0(_("sh_mem_free"));
441}
442
443void * sh_mem_malloc (size_t size)
444{
445 void * theAddress;
446
447 SL_ENTER(_("sh_mem_malloc"));
448
449 theAddress = malloc(size);
450
451 if ( theAddress == NULL )
452 {
453 if (eblock == 0)
454 {
455 eblock = 1;
456 (void) safe_logger(0, 0, getpid());
457 /*
458 sh_error_handle ((-1), FIL__, __LINE__, 0, MSG_E_MMEM);
459 */
460 eblock = 0;
461 }
462 /* use _exit() rather than exit() - we malloc() in atexit()
463 */
464 _exit (42);
465 }
466 /* memset (theAddress, 0, 1); *//* needs testing */
467
468 SL_RETURN( theAddress, _("sh_mem_malloc"));
469}
470#endif
Note: See TracBrowser for help on using the repository browser.