Annotation of parser3/src/targets/cgi/pool_storage.h, revision 1.6
1.1 parser 1: /** @file
1.6 ! paf 2: Parser: ISAPI: pool storage class decl.
1.1 parser 3:
4: Copyright (c) 2001 ArtLebedev Group (http://www.artlebedev.com)
1.5 paf 5: Author: Alexander Petrosyan <paf@design.ru> (http://paf.design.ru)
1.1 parser 6:
1.6 ! paf 7: $Id: pool_storage.h,v 1.13 2001/11/05 11:46:31 paf Exp $
1.1 parser 8: */
9:
10: #ifndef PA_POOL_STORAGE_H
11: #define PA_POOL_STORAGE_H
12:
13: #include "pa_config_includes.h"
14:
15: /**
16: Dumb pool allocations accounter
17:
18: @todo implement at least simple suballocations
19: */
1.4 parser 20: template<class T> class List {
21: public:
22: List(int preallocate) :
23: items((T *)::malloc(preallocate*sizeof(T))),
24: allocated(0),
25: used(0) {
26: if(items) // successfully preallocated?
27: allocated=preallocate;
28: }
1.2 parser 29:
1.4 parser 30: ~List() {
1.6 ! paf 31: if(items)
! 32: ::free(items);
! 33: items=0;
! 34: used=0;
1.4 parser 35: }
1.1 parser 36:
1.4 parser 37: bool add(T item) {
38: if(full())
39: if(!expand())
40: return false;
41:
42: items[used++]=item;
43: return true;
44: }
45:
46: void for_each_reverse(void (*callback)(T& info)) {
47: size_t top;
48:
49: for(top=used; top; )
50: callback(items[--top]);
51: }
52:
1.6 ! paf 53: size_t size() { return used; }
1.4 parser 54: private:
55:
56: bool full() { return used==allocated; }
57: bool expand() {
58: size_t new_allocated=allocated*3/2;
59: T *new_items=(T *)::realloc(items, new_allocated*sizeof(T));
60: if(new_items) {
61: items=new_items;
62: allocated=new_allocated;
1.1 parser 63: return true;
1.4 parser 64: } else
65: return false;
66: }
1.1 parser 67:
1.4 parser 68: private:
1.1 parser 69:
1.4 parser 70: T *items;
71: size_t allocated;
72: size_t used;
1.1 parser 73:
1.4 parser 74: };
1.1 parser 75:
1.2 parser 76: class Pool_storage {
1.6 ! paf 77:
1.1 parser 78: struct Cleanup_struct {
79: void (*cleanup) (void *);
80: void *data;
81: };
82:
83:
84: public:
85:
86: Pool_storage() :
1.6 ! paf 87: cleanups(100),
! 88: allocations(10*0x400) {
! 89: }
! 90:
! 91: void *malloc(size_t size) {
! 92: //fprintf(stderr, "malloc: %d\n", size);
! 93: void *result=::malloc(size);
! 94: if(result && !allocations.add(result)) {
! 95: ::free(result); result=0;
! 96: }
! 97: return result;
! 98: }
! 99: void *calloc(size_t size) {
! 100: void *result=::calloc(size, 1);
! 101: if(result && !allocations.add(result)) {
! 102: ::free(result); result=0;
! 103: }
! 104: return result;
1.1 parser 105: }
106:
107: bool register_cleanup(void (*cleanup) (void *), void *data) {
108: Cleanup_struct item={cleanup, data};
109: return cleanups.add(item)!=0;
110: }
111:
1.4 parser 112: static void cleanup(Cleanup_struct& item) {
113: item.cleanup(item.data);
114: }
115:
1.6 ! paf 116: static void free(void *& item) {
! 117: ::free(item); item=0;
! 118: }
! 119:
1.1 parser 120: ~Pool_storage() {
1.6 ! paf 121: // __asm__("int3");
! 122: //fprintf(stderr, "cleanups: %d\n", cleanups.size());
1.1 parser 123: // cleanups first, because they use some object's memory pointers
1.4 parser 124: cleanups.for_each_reverse(cleanup);
1.6 ! paf 125:
! 126: //fprintf(stderr, "allocs: %d\n", allocations.size());
! 127: // allocations
! 128: allocations.for_each_reverse(free);
1.1 parser 129: }
130:
131: private:
132:
133: List<Cleanup_struct> cleanups;
1.6 ! paf 134: List<void *> allocations;
1.1 parser 135:
136: };
137:
138:
139: #endif
E-mail: