1 karl 1.4 //%2006////////////////////////////////////////////////////////////////////////
|
2 mike 1.2 //
3 // Copyright (c) 2000, 2001, 2002 BMC Software; Hewlett-Packard Development
4 // Company, L.P.; IBM Corp.; The Open Group; Tivoli Systems.
5 // Copyright (c) 2003 BMC Software; Hewlett-Packard Development Company, L.P.;
6 // IBM Corp.; EMC Corporation, The Open Group.
7 // Copyright (c) 2004 BMC Software; Hewlett-Packard Development Company, L.P.;
8 // IBM Corp.; EMC Corporation; VERITAS Software Corporation; The Open Group.
9 // Copyright (c) 2005 Hewlett-Packard Development Company, L.P.; IBM Corp.;
10 // EMC Corporation; VERITAS Software Corporation; The Open Group.
|
11 karl 1.4 // Copyright (c) 2006 Hewlett-Packard Development Company, L.P.; IBM Corp.;
12 // EMC Corporation; Symantec Corporation; The Open Group.
|
13 mike 1.2 //
14 // Permission is hereby granted, free of charge, to any person obtaining a copy
15 // of this software and associated documentation files (the "Software"), to
16 // deal in the Software without restriction, including without limitation the
17 // rights to use, copy, modify, merge, publish, distribute, sublicense, and/or
18 // sell copies of the Software, and to permit persons to whom the Software is
19 // furnished to do so, subject to the following conditions:
20 //
21 // THE ABOVE COPYRIGHT NOTICE AND THIS PERMISSION NOTICE SHALL BE INCLUDED IN
22 // ALL COPIES OR SUBSTANTIAL PORTIONS OF THE SOFTWARE. THE SOFTWARE IS PROVIDED
23 // "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT
24 // LIMITED TO THE WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR
25 // PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
26 // HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN
27 // ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
28 // WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
29 //
30 //==============================================================================
31 //
32 // Author: Michael E. Brasher (mike-brasher@austin.rr.com -- Inova Europe)
33 //
34 mike 1.2 //%/////////////////////////////////////////////////////////////////////////////
35
36 #include <cstring>
37 #include "Buffer.h"
|
38 kumpf 1.4.2.1 #include "Pegasus/Common/InternalException.h"
|
39 mike 1.2
40 PEGASUS_NAMESPACE_BEGIN
41
42 BufferRep Buffer::_empty_rep = { 0, 0, {0} };
43
|
44 mike 1.3 static const size_t MIN_CAPACITY = 2048;
|
45 mike 1.2
46 static Uint32 _next_pow_2(Uint32 x)
47 {
48 if (x < MIN_CAPACITY)
49 return MIN_CAPACITY;
50
51 x--;
52 x |= (x >> 1);
53 x |= (x >> 2);
54 x |= (x >> 4);
55 x |= (x >> 8);
56 x |= (x >> 16);
57 x++;
58
59 return x;
60 }
61
62 static inline BufferRep* _allocate(size_t cap)
63 {
64 BufferRep* rep = (BufferRep*)malloc(sizeof(BufferRep) + cap);
|
65 kumpf 1.4.2.1 if (!rep)
66 {
67 throw PEGASUS_STD(bad_alloc)();
68 }
|
69 mike 1.2 rep->cap = cap;
70 return rep;
71 }
72
73 static inline BufferRep* _reallocate(BufferRep* rep, size_t cap)
74 {
75 rep = (BufferRep*)realloc(rep, sizeof(BufferRep) + cap);
|
76 kumpf 1.4.2.1 if (!rep)
77 {
78 throw PEGASUS_STD(bad_alloc)();
79 }
|
80 mike 1.2 rep->cap = cap;
81 return rep;
82 }
83
84 Buffer::Buffer(const Buffer& x)
85 {
86 _rep = _allocate(x._rep->cap);
87 memcpy(_rep->data, x._rep->data, x._rep->size);
88 _rep->size = x._rep->size;
89 }
90
91 Buffer::Buffer(const char* data, size_t size)
92 {
93 _rep = _allocate(size);
94 _rep->size = size;
95 memcpy(_rep->data, data, size);
96 }
97
98 Buffer& Buffer::operator=(const Buffer& x)
99 {
100 if (&x != this)
101 mike 1.2 {
102 if (x._rep->size > _rep->cap)
103 {
104 if (_rep != &_empty_rep)
105 free(_rep);
106
107 _rep = _allocate(x._rep->cap);
108 }
109
110 memcpy(_rep->data, x._rep->data, x._rep->size);
111 _rep->size = x._rep->size;
112 }
113 return *this;
114 }
115
116 void Buffer::_reserve_aux(size_t cap)
117 {
118 if (_rep == &_empty_rep)
119 {
120 _rep = _allocate(cap);
121 _rep->size = 0;
122 mike 1.2 }
123 else
124 _rep = _reallocate(_rep, _next_pow_2(cap));
125 }
126
127 void Buffer::_append_char_aux()
128 {
129 if (_rep == &_empty_rep)
130 {
131 _rep = _allocate(MIN_CAPACITY);
132 _rep->size = 0;
133 }
134 else
135 _rep = _reallocate(_rep, _rep->cap ? (2 * _rep->cap) : MIN_CAPACITY);
136 }
137
138 void Buffer::insert(size_t pos, const char* data, size_t size)
139 {
140 if (pos > _rep->size)
141 return;
142
143 mike 1.2 size_t cap = _rep->size + size;
144 size_t rem = _rep->size - pos;
145
146 if (cap > _rep->cap)
147 {
148 BufferRep* rep = _allocate(cap);
149 rep->size = cap;
150
151 memcpy(rep->data, _rep->data, pos);
152 memcpy(rep->data + pos, data, size);
153 memcpy(rep->data + pos + size, _rep->data + pos, rem);
154
155 if (_rep != &_empty_rep)
156 free(_rep);
157
158 _rep = rep;
159 }
160 else
161 {
162 memmove(_rep->data + pos + size, _rep->data + pos, rem);
163 memcpy(_rep->data + pos, data, size);
164 mike 1.2 _rep->size += size;
165 }
166 }
167
168 void Buffer::remove(size_t pos, size_t size)
169 {
170 if (pos + size > _rep->size)
171 return;
172
173 size_t rem = _rep->size - (pos + size);
174
175 if (rem)
176 memmove(_rep->data + pos, _rep->data + pos + size, rem);
177
178 _rep->size -= size;
179 }
180
181 PEGASUS_NAMESPACE_END
|