~clint-fewbar/ubuntu/precise/squid3/ignore-sighup-early

« back to all changes in this revision

Viewing changes to src/cbdata.h

  • Committer: Bazaar Package Importer
  • Author(s): Luigi Gangitano
  • Date: 2009-09-24 14:51:06 UTC
  • mfrom: (1.1.12 upstream)
  • mto: (20.2.1 sid)
  • mto: This revision was merged to the branch mainline in revision 21.
  • Revision ID: james.westby@ubuntu.com-20090924145106-38jgrzmj0d73pha5
Tags: 3.1.0.13-1
* Upload to experimental

* New upstream release
  - Fixes Follow-X-Forwarded-For support (Closes: #523943)
  - Adds IPv6 support (Closes: #432351)

* debian/rules
  - Removed obsolete configuration options
  - Enable db and radius basic authentication modules

* debian/patches/01-cf.data.debian
  - Adapted to new upstream version

* debian/patches/02-makefile-defaults
  - Adapted to new upstream version

* debian/{squid.postinst,squid.rc,README.Debian,watch}
  - Updated references to squid 3.1

* debian/squid3.install
  - Install CSS file for error pages
  - Install manual pages for new authentication modules

* debian/squid3-common.install
  - Install documented version of configuration file in /usr/share/doc/squid3

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
 
 
2
1
/*
3
 
 * $Id: cbdata.h,v 1.1 2006/08/21 00:50:41 robertc Exp $
 
2
 * $Id$
4
3
 *
5
4
 *
6
5
 * SQUID Web Proxy Cache          http://www.squid-cache.org/
19
18
 *  it under the terms of the GNU General Public License as published by
20
19
 *  the Free Software Foundation; either version 2 of the License, or
21
20
 *  (at your option) any later version.
22
 
 *  
 
21
 *
23
22
 *  This program is distributed in the hope that it will be useful,
24
23
 *  but WITHOUT ANY WARRANTY; without even the implied warranty of
25
24
 *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
26
25
 *  GNU General Public License for more details.
27
 
 *  
 
26
 *
28
27
 *  You should have received a copy of the GNU General Public License
29
28
 *  along with this program; if not, write to the Free Software
30
29
 *  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111, USA.
37
36
 
38
37
#include "squid.h"
39
38
 
40
 
/*
 
39
/**
 
40
 \defgroup CBDATAAPI Callback Data Allocator API
 
41
 \ingroup Components
 
42
 \par
 
43
 *    Squid's extensive use of callback functions makes it very
 
44
 *    susceptible to memory access errors. To address this all callback
 
45
 *    functions make use of a construct called cbdata. This allows
 
46
 *    functions doing callbacks to verify that the caller is still
 
47
 *    valid before making the callback.
 
48
 *
 
49
 \note  cbdata is intended for callback data and is tailored specifically
 
50
 *      to make callbacks less dangerous leaving as few windows of errors as
 
51
 *      possible. It is not suitable or intended as a generic RefCount
 
52
 *      memory allocator.
 
53
 *
 
54
 \todo CODE: make cbdata a template or class-inheritance system instead of Macros.
 
55
 *
 
56
 \section Examples Examples
 
57
 \par
 
58
 *      Here you can find some examples on how to use cbdata, and why.
 
59
 *
 
60
 \subsection AsyncOpWithoutCBDATA Asynchronous operation without cbdata, showing why cbdata is needed
 
61
 \par
 
62
 *      For a asyncronous operation with callback functions, the normal
 
63
 *      sequence of events in programs NOT using cbdata is as follows:
 
64
 *
 
65
 \code
 
66
        // initialization
 
67
        type_of_data our_data;
 
68
        ...
 
69
        our_data = malloc(...);
 
70
        ...
 
71
        // Initiate a asyncronous operation, with our_data as callback_data
 
72
        fooOperationStart(bar, callback_func, our_data);
 
73
        ...
 
74
        // The asyncronous operation completes and makes the callback
 
75
        callback_func(callback_data, ....);
 
76
        // Some time later we clean up our data
 
77
        free(our_data);
 
78
 \endcode
 
79
 *
 
80
 \par
 
81
 *      However, things become more interesting if we want or need
 
82
 *      to free the callback_data, or otherwise cancel the callback,
 
83
 *      before the operation completes. In constructs like this you
 
84
 *      can quite easily end up with having the memory referenced
 
85
 *      pointed to by callback_data freed before the callback is invoked
 
86
 *      causing a program failure or memory corruption:
 
87
 *
 
88
 \code
 
89
        // initialization
 
90
        type_of_data our_data;
 
91
        ...
 
92
        our_data = malloc(...);
 
93
        ...
 
94
        // Initiate a asyncronous operation, with our_data as callback_data
 
95
        fooOperationStart(bar, callback_func, our_data);
 
96
        ...
 
97
        // ouch, something bad happened elsewhere.. try to cleanup
 
98
        // but the programmer forgot there is a callback pending from
 
99
        // fooOperationsStart() (an easy thing to forget when writing code
 
100
        // to deal with errors, especially if there may be many different
 
101
        // pending operation)
 
102
        free(our_data);
 
103
        ...
 
104
        // The asyncronous operation completes and makes the callback
 
105
        callback_func(callback_data, ....);
 
106
        // CRASH, the memory pointer to by callback_data is no longer valid
 
107
        // at the time of the callback
 
108
 \endcode
 
109
 *
 
110
 \subsection AsyncOpWithCBDATA Asyncronous operation with cbdata
 
111
 *
 
112
 \par
 
113
 *      The callback data allocator lets us do this in a uniform and
 
114
 *      safe manner.  The callback data allocator is used to allocate,
 
115
 *      track and free memory pool objects used during callback
 
116
 *      operations.  Allocated memory is locked while the asyncronous
 
117
 *      operation executes elsewhere, and is freed when the operation
 
118
 *      completes.  The normal sequence of events is:
 
119
 *
 
120
 \code
 
121
        // initialization
 
122
        type_of_data our_data;
 
123
        ...
 
124
        our_data = cbdataAlloc(type_of_data);
 
125
        ...
 
126
        // Initiate a asyncronous operation, with our_data as callback_data
 
127
        fooOperationStart(..., callback_func, our_data);
 
128
        ...
 
129
        // foo
 
130
        void *local_pointer = cbdataReference(callback_data);
 
131
        ....
 
132
        // The asyncronous operation completes and makes the callback
 
133
        void *cbdata;
 
134
        if (cbdataReferenceValidDone(local_pointer, &cbdata))
 
135
            callback_func(...., cbdata);
 
136
        ...
 
137
        cbdataFree(our_data);
 
138
 \endcode
 
139
 *
 
140
 \subsection AsynchronousOpCancelledByCBDATA Asynchronous operation cancelled by cbdata
 
141
 *
 
142
 \par
 
143
 *      With this scheme, nothing bad happens if cbdataFree() gets called
 
144
 *      before fooOperantionComplete(...).
 
145
 *
 
146
 \par   Initalization
 
147
 \code
 
148
        type_of_data our_data;
 
149
        ...
 
150
        our_data = cbdataAlloc(type_of_data);
 
151
 \endcode
 
152
 *      Initiate a asyncronous operation, with our_data as callback_data
 
153
 \code
 
154
        fooOperationStart(..., callback_func, our_data);
 
155
 \endcode
 
156
 *      do some stuff with it
 
157
 \code
 
158
        void *local_pointer = cbdataReference(callback_data);
 
159
 \endcode
 
160
 *      something bad happened elsewhere.. cleanup
 
161
 \code
 
162
        cbdataFree(our_data);
 
163
 \endcode
 
164
 *      The asyncronous operation completes and tries to make the callback
 
165
 \code
 
166
        void *cbdata;
 
167
        if (cbdataReferenceValidDone(local_pointer, &cbdata))
 
168
        {
 
169
 \endcode
 
170
 *      won't be called, as the data is no longer valid
 
171
 \code
 
172
            callback_func(...., cbdata);
 
173
        }
 
174
 \endcode
 
175
 *
 
176
 \par
 
177
 *      In this case, when cbdataFree() is called before
 
178
 *      cbdataReferenceValidDone(), the callback_data gets marked as invalid.
 
179
 *      When the callback_data is invalid before executing the callback
 
180
 *      function, cbdataReferenceValidDone() will return 0 and
 
181
 *      callback_func is never executed.
 
182
 *
 
183
 \subsection AddingCBDATAType Adding a new cbdata registered type
 
184
 *
 
185
 \par
 
186
 *      To add new module specific data types to the allocator one uses the
 
187
 *      macros CBDATA_TYPE() and CBDATA_INIT_TYPE(). These creates a local cbdata
 
188
 *      definition (file or block scope). Any cbdataAlloc() calls must be made
 
189
 *      within this scope. However, cbdataFree() might be called from anywhere.
 
190
 *
 
191
 \par
 
192
 *      First the cbdata type needs to be defined in the module. This
 
193
 *      is usually done at file scope, but it can also be local to a
 
194
 *      function or block..
 
195
 \code
 
196
        CBDATA_TYPE(type_of_data);
 
197
 \endcode
 
198
 *      Then in the code somewhere before the first allocation
 
199
 *      (can be called multiple times with only a minimal overhead)
 
200
 \code
 
201
        CBDATA_INIT_TYPE(type_of_data);
 
202
 \endcode
 
203
 *      Or if a free function is associated with the data type. This
 
204
 *      function is responsible for cleaning up any dependencies etc
 
205
 *      referenced by the structure and is called on cbdataFree() or
 
206
 *      when the last reference is deleted by cbdataReferenceDone() /
 
207
 *      cbdataReferenceValidDone()
 
208
 \code
 
209
        CBDATA_INIT_TYPE_FREECB(type_of_data, free_function);
 
210
 \endcode
 
211
 *
 
212
 \subsection AddingGlobalCBDATATypes Adding a new cbdata registered data type globally
 
213
 *
 
214
 \par
 
215
 *      To add new global data types that can be allocated from anywhere
 
216
 *      within the code one have to add them to the cbdata_type enum in
 
217
 *      enums.h, and a corresponding CREATE_CBDATA() call in
 
218
 *      cbdata.c:cbdataInit(). Or alternatively add a CBDATA_GLOBAL_TYPE()
 
219
 *      definition to globals.h as shown below and use CBDATA_INIT_TYPE() at
 
220
 *      the appropriate location(s) as described above.
 
221
 *
 
222
 \code
 
223
        extern CBDATA_GLOBAL_TYPE(type_of_data);        // CBDATA_UNDEF
 
224
 \endcode
 
225
 */
 
226
 
 
227
/**
 
228
 *\ingroup CBDATAAPI
41
229
 * cbdata types. similar to the MEM_* types above, but managed
42
230
 * in cbdata.c. A big difference is that these types are dynamically
43
231
 * allocated. This list is only a list of predefined types. Other types
47
235
    CBDATA_UNKNOWN = 0
48
236
} cbdata_type;
49
237
 
50
 
extern void cbdataRegisterWithCacheManager(CacheManager & manager);
 
238
/// \ingroup CBDATAAPI
 
239
extern void cbdataRegisterWithCacheManager(void);
 
240
 
51
241
#if CBDATA_DEBUG
52
242
extern void *cbdataInternalAllocDbg(cbdata_type type, const char *, int);
53
243
extern void *cbdataInternalFreeDbg(void *p, const char *, int);
55
245
extern void cbdataInternalUnlockDbg(const void *p, const char *, int);
56
246
extern int cbdataInternalReferenceDoneValidDbg(void **p, void **tp, const char *, int);
57
247
#else
 
248
 
 
249
/// \ingroup CBDATAAPI
58
250
extern void *cbdataInternalAlloc(cbdata_type type);
 
251
 
 
252
/// \ingroup CBDATAAPI
59
253
extern void *cbdataInternalFree(void *p);
 
254
 
 
255
/// \ingroup CBDATAAPI
60
256
extern void cbdataInternalLock(const void *p);
 
257
 
 
258
/// \ingroup CBDATAAPI
61
259
extern void cbdataInternalUnlock(const void *p);
 
260
 
 
261
/// \ingroup CBDATAAPI
62
262
extern int cbdataInternalReferenceDoneValid(void **p, void **tp);
63
 
#endif
 
263
 
 
264
#endif /* !CBDATA_DEBUG */
 
265
 
 
266
/**
 
267
 \ingroup CBDATAAPI
 
268
 *
 
269
 \param p       A cbdata entry reference pointer.
 
270
 *
 
271
 \retval 0      A reference is stale. The pointer refers to a entry freed by cbdataFree().
 
272
 \retval true   The reference is valid and active.
 
273
 */
64
274
extern int cbdataReferenceValid(const void *p);
 
275
 
 
276
/// \ingroup CBDATAAPI
65
277
extern cbdata_type cbdataInternalAddType(cbdata_type type, const char *label, int size, FREE * free_func);
66
278
 
67
279
 
83
295
                void operator delete (void *address) { \
84
296
                  if (address) cbdataInternalFreeDbg(address,__FILE__,__LINE__); \
85
297
                } \
 
298
                void *toCbdata() { return this; } \
86
299
        private:
87
300
#else
 
301
 
 
302
/**
 
303
 \ingroup CBDATAAPI
 
304
 * Allocates a new entry of a registered CBDATA type.
 
305
 */
88
306
#define cbdataAlloc(type) ((type *)cbdataInternalAlloc(CBDATA_##type))
 
307
 
 
308
/**
 
309
 \ingroup CBDATAAPI
 
310
 \par
 
311
 *    Frees a entry allocated by cbdataAlloc().
 
312
 *
 
313
 \note  If there are active references to the entry then the entry
 
314
 *      will be freed with the last reference is removed. However,
 
315
 *      cbdataReferenceValid() will return false for those references.
 
316
 */
89
317
#define cbdataFree(var)         do {if (var) {cbdataInternalFree(var); var = NULL;}} while(0)
 
318
 
 
319
/**
 
320
 \ingroup CBDATAAPI
 
321
 * Removes a reference created by cbdataReference() and checks
 
322
 * it for validity. Meant to be used on the last dereference,
 
323
 * usually to make a callback.
 
324
 *
 
325
 \code
 
326
        void *cbdata;
 
327
        ...
 
328
        if (cbdataReferenceValidDone(reference, &cbdata)) != NULL)
 
329
            callback(..., cbdata);
 
330
 \endcode
 
331
 *
 
332
 \param var     The reference variable. Will be automatically cleared to NULL.
 
333
 \param ptr     A temporary pointer to the referenced data (if valid).
 
334
 */
90
335
#define cbdataReferenceValidDone(var, ptr) cbdataInternalReferenceDoneValid((void **)&(var), (ptr))
91
336
 
92
 
/**
93
 
 * This needs to be defined LAST in teh class definition. It plays with private/public states in C++.
94
 
 */
 
337
/// \ingroup CBDATAAPI
95
338
#define CBDATA_CLASS2(type)     \
96
 
        private: \
97
339
        static cbdata_type CBDATA_##type; \
98
340
        public: \
99
341
                void *operator new(size_t size) { \
103
345
                } \
104
346
                void operator delete (void *address) { \
105
347
                  if (address) cbdataInternalFree(address);\
106
 
                }
107
 
#endif
 
348
                } \
 
349
                void *toCbdata() { return this; } \
 
350
        private:
 
351
#endif /* !CBDATA_DEBUG */
 
352
 
 
353
/**
 
354
 \ingroup CBDATAAPI
 
355
 \par
 
356
 *    Creates a new reference to a cbdata entry. Used when you need to
 
357
 *    store a reference in another structure. The reference can later
 
358
 *    be verified for validity by cbdataReferenceValid().
 
359
 *
 
360
 \param var
 
361
 *       The reference variable is a pointer to the entry, in all
 
362
 *       aspects identical to the original pointer. But semantically it
 
363
 *       is quite different. It is best if the reference is thought of
 
364
 *       and handled as a "void *".
 
365
 */
108
366
#define cbdataReference(var)    (cbdataInternalLock(var), var)
 
367
 
 
368
/**
 
369
 \ingroup CBDATAAPI
 
370
 * Removes a reference created by cbdataReference().
 
371
 *
 
372
 \param var     The reference variable. Will be automatically cleared to NULL.
 
373
 */
109
374
#define cbdataReferenceDone(var) do {if (var) {cbdataInternalUnlock(var); var = NULL;}} while(0)
 
375
 
 
376
/// \ingroup CBDATAAPI
110
377
#define CBDATA_CLASS(type)      static cbdata_type CBDATA_##type
 
378
 
 
379
/// \ingroup CBDATAAPI
111
380
#define CBDATA_CLASS_INIT(type) cbdata_type type::CBDATA_##type = CBDATA_UNKNOWN
 
381
#define CBDATA_NAMESPACED_CLASS_INIT(namespace, type) cbdata_type namespace::type::CBDATA_##type = CBDATA_UNKNOWN
 
382
 
 
383
/**
 
384
 \ingroup CBDATAAPI
 
385
 * Macro that defines a new cbdata datatype. Similar to a variable
 
386
 * or struct definition. Scope is always local to the file/block
 
387
 * where it is defined and all calls to cbdataAlloc() for this type
 
388
 * must be within the same scope as the CBDATA_TYPE declaration.
 
389
 * Allocated entries may be referenced or freed anywhere with no
 
390
 * restrictions on scope.
 
391
 */
112
392
#define CBDATA_TYPE(type)       static cbdata_type CBDATA_##type = CBDATA_UNKNOWN
 
393
 
 
394
/**
 
395
 \ingroup CBDATAAPI
 
396
 * Defines a global cbdata type that can be referenced anywhere in the code.
 
397
 *
 
398
 \code
 
399
        external CBDATA_GLOBAL_TYPE(datatype);
 
400
 \endcode
 
401
 * Should be added to the module *.h header file.
 
402
 *
 
403
 \code
 
404
        CBDATA_GLOBAL_TYPE(datatype);
 
405
 \endcode
 
406
 *
 
407
 *  Should be added to the module main *.cc file.
 
408
 */
113
409
#define CBDATA_GLOBAL_TYPE(type)        cbdata_type CBDATA_##type
 
410
 
 
411
/**
 
412
 \ingroup CBDATAAPI
 
413
 *
 
414
 * Initializes the cbdatatype. Must be called prior to the first use of cbdataAlloc() for the type.
 
415
 *
 
416
 \par
 
417
 * Alternative to CBDATA_INIT_TYPE_FREECB()
 
418
 *
 
419
 \param type            Type being initialized
 
420
 */
114
421
#define CBDATA_INIT_TYPE(type)  (CBDATA_##type ?  CBDATA_UNKNOWN : (CBDATA_##type = cbdataInternalAddType(CBDATA_##type, #type, sizeof(type), NULL)))
 
422
 
 
423
/**
 
424
 \ingroup CBDATAAPI
 
425
 *
 
426
 * Initializes the cbdatatype. Must be called prior to the first use of cbdataAlloc() for the type.
 
427
 *
 
428
 \par
 
429
 * Alternative to CBDATA_INIT_TYPE()
 
430
 *
 
431
 \param type            Type being initialized
 
432
 \param free_func       The freehandler called when the last known reference to an allocated entry goes away.
 
433
 */
115
434
#define CBDATA_INIT_TYPE_FREECB(type, free_func)        (CBDATA_##type ?  CBDATA_UNKNOWN : (CBDATA_##type = cbdataInternalAddType(CBDATA_##type, #type, sizeof(type), free_func)))
116
435
 
117
 
/*
118
 
 * use this when you need to pass callback data to a blocking
 
436
/**
 
437
 \ingroup CBDATA
 
438
 *
 
439
 * A generic wrapper for passing objects through cbdata.
 
440
 * Use this when you need to pass callback data to a blocking
119
441
 * operation, but you don't want to/cannot have that pointer be cbdata itself.
120
442
 */
121
 
 
122
443
class generic_cbdata
123
444
{
124
 
  public:
 
445
public:
 
446
 
125
447
    generic_cbdata(void * data) : data(data) {}
126
 
    template<typename wrapped_type>void unwrap(wrapped_type **output) 
127
 
      {
128
 
        *output = static_cast<wrapped_type *>(data);
129
 
        delete this;
130
 
      }
131
 
    /* the wrapped data - only public to allow the mild abuse of this facility
 
448
 
 
449
    template<typename wrapped_type>void unwrap(wrapped_type **output) {
 
450
        *output = static_cast<wrapped_type *>(data);
 
451
        delete this;
 
452
    }
 
453
 
 
454
    /**
 
455
     * The wrapped data - only public to allow the mild abuse of this facility
132
456
     * done by store_swapout - it gives a wrapped StoreEntry to StoreIO as the
133
457
     * object to be given to the callbacks. That needs to be fully cleaned up!
134
458
     * - RBC 20060820
 
459
     \todo CODE: make this a private field.
135
460
     */
136
461
    void *data; /* the wrapped data */
137
 
 
 
462
private:
138
463
    CBDATA_CLASS2(generic_cbdata);
139
464
};
140
465
 
141
 
 
142
 
 
143
466
#endif /* SQUID_CBDATA_H */