This file is indexed.

/usr/include/dar/on_pool.hpp is in libdar-dev 2.5.3-1ubuntu1.

This file is owned by root:root, with mode 0o644.

The actual contents of the file can be viewed below.

  1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
/*********************************************************************/
// dar - disk archive - a backup/restoration program
// Copyright (C) 2002-2052 Denis Corbin
//
// This program is free software; you can redistribute it and/or
// modify it under the terms of the GNU General Public License
// as published by the Free Software Foundation; either version 2
// of the License, or (at your option) any later version.
//
// This program is distributed in the hope that it will be useful,
// but WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
// GNU General Public License for more details.
//
// You should have received a copy of the GNU General Public License
// along with this program; if not, write to the Free Software
// Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA.
//
// to contact the author : http://dar.linux.free.fr/email.html
/*********************************************************************/

    /// \file on_pool.hpp
    /// \brief this is the base class of object that can be allocated on a memory pool
    /// \ingroup Private



#ifndef ON_POOL_HPP
#define ON_POOL_HPP

#include "/usr/include/dar/libdar_my_config.h"
#include <vector>
#include <new>
#include "/usr/include/dar/integers.hpp"
#include "/usr/include/dar/memory_pool.hpp"
#include "/usr/include/dar/mem_allocator.hpp"
#include "/usr/include/dar/cygwin_adapt.hpp"


namespace libdar
{


	/// \addtogroup Private
	/// @{

	/// class on_pool is the ancestors of all class that are able to be allocated on a memory pool
	///
	/// \note: new and new[] operators using memory pool never throw an exception upon allocation failure
	/// but rather return nullptr pointer. This is the way it was working before g++03 and g++11

    class on_pool
    {
    public:
#ifdef LIBDAR_SPECIAL_ALLOC

	    /// constructor
	    ///
	    /// \note If an object has been created by new (not new[], temporary, or local variable)
	    /// the get_pool() method can return the pool used for allocation, else it returns nullptr.
	    /// The consequence is that objects dynamically created within an array (new []) cannot know
	    /// the whether they have been allocated using a memory pool or not
	on_pool() { dynamic_init(); };

	    /// copy constructor
	    ///
	    /// \note the default copy constructor is not adequate as it would copy the value of dynamic
	    /// of the source object whatever is the way the new object is created (dynamically allocated or not)
	on_pool(const on_pool & ref) { dynamic_init(); };

	    /// the assignment operator
	    ///
	    /// \note the assignement operator must not modify the field "dynamic" so we must not use
	    /// the default operator
	const on_pool & operator = (const on_pool & ref) { return *this; };

	    /// virtual destructor as this class will have inherited classes
	virtual ~on_pool() throw(Ebug) {};
#endif

	    /// the usual new operator is wrapped to allow proper delete operation later on (throws std::bad_alloc upon allocation failure)
	    ///
	    /// \note memory allocation done this way does not use the default C++ new[] operator, which may be slower than using memory pool
	void *operator new(size_t n_byte) { void *ret = alloc(n_byte, nullptr); if(ret == nullptr) throw std::bad_alloc(); return ret; };


	    /// the usual new operator is wrapped to allow proper delete operation later on (does not throw exception upon allocation failure)
	    ///
	    /// \note memory allocation done this way does not use the default C++ new[] operator, which may be slower than using memory pool
	void *operator new(size_t n_byte, const std::nothrow_t & nothrow_value) { return alloc(n_byte, nullptr); };


	    /// the usual new[] operator is wrapped to allow proper delete[] operation later on (throws std::bad_alloc upon allocation failure)
	    ///
	    /// \note memory allocation done this way does not use the default C++ new[] operator, which may be slower than using memory pool
	void *operator new[](size_t n_byte) { void *ret = alloc(n_byte, nullptr); if(ret == nullptr) throw std::bad_alloc(); return ret; };


	    /// the usual new[] operator is wrapped to allow proper delete[] operation later on (does not throw exception upon allocation failure)
	    ///
	    /// \note memory allocation done this way does not use the default C++ new[] operator, which may be slower than using memory pool
	void *operator new[](size_t n_byte, const std::nothrow_t & nothrow_value) { return alloc(n_byte, nullptr); };

	    /// this operator allocates a single object on a memory pool
	    ///
	    /// \note usage is: type *ptr = new (pool_obj) type(initial,values)
	    /// \note such object has to be delete normally no need to call the destructor manually
	void *operator new(size_t n_byte, memory_pool *p) { return alloc(n_byte, p); };


	    /// this operator allocates an array of objects on a memory pool
	    ///
	    /// \note usage is: type *ptr = new (pool_obj) type(initial,values)
	    /// \note such object has to be delete normally no need to call the destructor manually
	void *operator new[] (size_t n_byte, memory_pool *p) { return alloc(n_byte, p); };


	    /// this operator is called by the compiler if an exception is throw from the constructor of the allocated object
	void operator delete(void *ptr, memory_pool *p) { dealloc(ptr); };


	    /// this operator is called by the compiler if an exception is throw from the constructor of the allocated objects
	void operator delete[](void *ptr, memory_pool *p) { dealloc(ptr); };


	    /// this is the usual delete operator, modified to handle allocated objects allocated on a memory pool or not
	void operator delete(void *ptr) { dealloc(ptr); };


	    /// this is the usual delete[] operator, modified to handle allocated objects allocated on a memory pool or not
	void operator delete[](void *ptr) { dealloc(ptr); };

    protected:
	    /// get the pool used to allocate "this"
	    ///
	    /// \return the address of the memory pool that has been used to allocate the object
	    /// \note if the object has not been allocated using a memory pool nullptr is returned
	    /// \note if the object has not been dynamically allocated, that's to say is a local variable
	    /// or a temporary object, get_pool() must not be called as it will return unpredictable
	    /// result and could most probably crash the application if the returned data is used
#ifdef LIBDAR_SPECIAL_ALLOC
	memory_pool *get_pool() const { return dynamic ? (((pool_ptr *)this) - 1)->reserve : nullptr; };
#else
	memory_pool *get_pool() const { return nullptr; };
#endif

	template <class T> void meta_new(T * & ptr, size_t num)
	{
#ifdef LIBDAR_SPECIAL_ALLOC
	    size_t byte = num * sizeof(T);

	    if(get_pool() != nullptr)
		ptr = (T *)get_pool()->alloc(byte);
	    else
		ptr = (T *)new (std::nothrow) char [byte];
#else
	    ptr = new (std::nothrow) T[num];
#endif
	}



	template <class T> void meta_delete(T * ptr)
	{
#ifdef LIBDAR_SPECIAL_ALLOC
	    if(get_pool() != nullptr)
		get_pool()->release(ptr);
	    else
		delete [] (char *)(ptr);
#else
	    delete [] ptr;
#endif
	}

    private:
#ifdef LIBDAR_SPECIAL_ALLOC

	    /// this data structure is placed at the beginning of any allocated block
	    ///
	    /// \note thanks to this structure, it is possible to know which memory pool has to be
	    /// informed of the memory release in order for the memory block to be recyclable
	union pool_ptr
	{
	    memory_pool *reserve; //< this is to be able to pass the pool object to the constructor if it requires dynamic memory allocation
	    U_I  alignment__i; //< to properly align the allocated memory block that follows
	    U_32 alignment_32; //< to properly align the allocated memory block that follows
	    U_64 alignment_64; //< to properly align the allocated memory block that follows
	};

	    // this field is necessary to make distinction between object on the heap that have a pool_ptr header from those
	    // created as local or temporary variable (on the stack).
	bool dynamic;

	    /// used from constructors to setup field "dynamic"
	void dynamic_init() const { const_cast<on_pool *>(this)->dynamic = (alloc_not_constructed == this); alloc_not_constructed = nullptr; };
#endif

	    /// does the whole magic of memory allocation with and without memory_pool
	    ///
	    /// \param[in] size is the size of the requested block of memory to allocate
	    /// \param[in] is the address of the pool to request the memory block to, nullptr if default memory allocation shall be used
	    /// \return the address of the allocated memory block is returned, nullptr is returned upon memory allocation failure
	static void *alloc(size_t size, memory_pool *p);

	    /// does the whole magic of memory release with and without memory_pool
	    ///
	    /// \param[in] ptr is the address of the memory block to release
	    /// \note may throw exceptions if the given address has never been allocated or is nullptr
	static void dealloc(void *ptr);

#ifdef LIBDAR_SPECIAL_ALLOC
#ifdef CYGWIN_BUILD
	static on_pool *alloc_not_constructed;
	    // under cygwin the thread_local directive does not work but
	    // as we build only command-line tools that are single threaded
	    // program, it does not hurt using global static field here
	    // well, as soon as another application than dar/dar_xform/...
	    // relies on a cygwin build of libdar, this trick should be changed
#else
	thread_local static on_pool * alloc_not_constructed;
#endif
#endif
    };

	/// @}

} // end of namespace

#endif