OLD | NEW |
1 // Copyright 2013 The Chromium Authors. All rights reserved. | 1 // Copyright 2013 The Chromium Authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #ifndef MOJO_SYSTEM_MEMORY_H_ | 5 #ifndef MOJO_SYSTEM_MEMORY_H_ |
6 #define MOJO_SYSTEM_MEMORY_H_ | 6 #define MOJO_SYSTEM_MEMORY_H_ |
7 | 7 |
8 #include <stddef.h> | 8 #include <stddef.h> |
9 #include <stdint.h> | 9 #include <stdint.h> |
10 #include <string.h> // For |memcpy()|. | 10 #include <string.h> // For |memcpy()|. |
(...skipping 11 matching lines...) Expand all Loading... |
22 // Removes |const| from |T| (available as |remove_const<T>::type|): | 22 // Removes |const| from |T| (available as |remove_const<T>::type|): |
23 // TODO(vtl): Remove these once we have the C++11 |remove_const|. | 23 // TODO(vtl): Remove these once we have the C++11 |remove_const|. |
24 template <typename T> struct remove_const { typedef T type; }; | 24 template <typename T> struct remove_const { typedef T type; }; |
25 template <typename T> struct remove_const<const T> { typedef T type; }; | 25 template <typename T> struct remove_const<const T> { typedef T type; }; |
26 | 26 |
27 // Yields |(const) char| if |T| is |(const) void|, else |T|: | 27 // Yields |(const) char| if |T| is |(const) void|, else |T|: |
28 template <typename T> struct VoidToChar { typedef T type; }; | 28 template <typename T> struct VoidToChar { typedef T type; }; |
29 template <> struct VoidToChar<void> { typedef char type; }; | 29 template <> struct VoidToChar<void> { typedef char type; }; |
30 template <> struct VoidToChar<const void> { typedef const char type; }; | 30 template <> struct VoidToChar<const void> { typedef const char type; }; |
31 | 31 |
| 32 // Checks (insofar as appropriate/possible) that |pointer| is a valid pointer to |
| 33 // a buffer of the given size and alignment (both in bytes). |
32 template <size_t size, size_t alignment> | 34 template <size_t size, size_t alignment> |
33 void MOJO_SYSTEM_IMPL_EXPORT CheckUserPointerHelper(const void* pointer); | 35 void MOJO_SYSTEM_IMPL_EXPORT CheckUserPointer(const void* pointer); |
34 | 36 |
| 37 // Checks (insofar as appropriate/possible) that |pointer| is a valid pointer to |
| 38 // a buffer of |count| elements of the given size and alignment (both in bytes). |
35 template <size_t size, size_t alignment> | 39 template <size_t size, size_t alignment> |
36 void MOJO_SYSTEM_IMPL_EXPORT CheckUserPointerWithCountHelper( | 40 void MOJO_SYSTEM_IMPL_EXPORT CheckUserPointerWithCount(const void* pointer, |
37 const void* pointer, | 41 size_t count); |
38 size_t count); | 42 |
| 43 // Checks (insofar as appropriate/possible) that |pointer| is a valid pointer to |
| 44 // a buffer of the given size and alignment (both in bytes). |
| 45 template <size_t alignment> |
| 46 void MOJO_SYSTEM_IMPL_EXPORT CheckUserPointerWithSize(const void* pointer, |
| 47 size_t size); |
39 | 48 |
40 // TODO(vtl): Delete all the |Verify...()| things (and replace them with | 49 // TODO(vtl): Delete all the |Verify...()| things (and replace them with |
41 // |Check...()|. | 50 // |Check...()|. |
42 template <size_t size, size_t alignment> | 51 template <size_t size, size_t alignment> |
43 bool MOJO_SYSTEM_IMPL_EXPORT VerifyUserPointerHelper(const void* pointer); | 52 bool MOJO_SYSTEM_IMPL_EXPORT VerifyUserPointerHelper(const void* pointer); |
44 | 53 |
45 // Note: This is also used by options_validation.h. | 54 // Note: This is also used by options_validation.h. |
46 template <size_t size, size_t alignment> | 55 template <size_t size, size_t alignment> |
47 bool MOJO_SYSTEM_IMPL_EXPORT VerifyUserPointerWithCountHelper( | 56 bool MOJO_SYSTEM_IMPL_EXPORT VerifyUserPointerWithCountHelper( |
48 const void* pointer, | 57 const void* pointer, |
49 size_t count); | 58 size_t count); |
50 | 59 |
51 } // namespace internal | 60 } // namespace internal |
52 | 61 |
53 // Forward declarations so that they can be friended. | 62 // Forward declarations so that they can be friended. |
54 template <typename Type> class UserPointerReader; | 63 template <typename Type> class UserPointerReader; |
55 template <typename Type> class UserPointerWriter; | 64 template <typename Type> class UserPointerWriter; |
56 template <typename Type> class UserPointerReaderWriter; | 65 template <typename Type> class UserPointerReaderWriter; |
| 66 template <class Options> class UserOptionsReader; |
57 | 67 |
58 // Verify (insofar as possible/necessary) that a |T| can be read from the user | 68 // Verify (insofar as possible/necessary) that a |T| can be read from the user |
59 // |pointer|. | 69 // |pointer|. |
60 template <typename T> | 70 template <typename T> |
61 bool VerifyUserPointer(const T* pointer) { | 71 bool VerifyUserPointer(const T* pointer) { |
62 return internal::VerifyUserPointerHelper<sizeof(T), MOJO_ALIGNOF(T)>(pointer); | 72 return internal::VerifyUserPointerHelper<sizeof(T), MOJO_ALIGNOF(T)>(pointer); |
63 } | 73 } |
64 | 74 |
65 // Verify (insofar as possible/necessary) that |count| |T|s can be read from the | 75 // Verify (insofar as possible/necessary) that |count| |T|s can be read from the |
66 // user |pointer|; |count| may be zero. (This is done carefully since |count * | 76 // user |pointer|; |count| may be zero. (This is done carefully since |count * |
(...skipping 44 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
111 | 121 |
112 // Allow conversion to a "non-const" |UserPointer|. | 122 // Allow conversion to a "non-const" |UserPointer|. |
113 operator UserPointer<const Type>() const { | 123 operator UserPointer<const Type>() const { |
114 return UserPointer<const Type>(pointer_); | 124 return UserPointer<const Type>(pointer_); |
115 } | 125 } |
116 | 126 |
117 bool IsNull() const { | 127 bool IsNull() const { |
118 return !pointer_; | 128 return !pointer_; |
119 } | 129 } |
120 | 130 |
| 131 // "Reinterpret casts" to a |UserPointer<ToType>|. |
| 132 template <typename ToType> |
| 133 UserPointer<ToType> ReinterpretCast() const { |
| 134 return UserPointer<ToType>(reinterpret_cast<ToType*>(pointer_)); |
| 135 } |
| 136 |
| 137 // Checks that this pointer points to a valid array (of type |Type|, or just a |
| 138 // buffer if |Type| is |void| or |const void|) of |count| elements (or bytes |
| 139 // if |Type| is |void| or |const void|) in the same way as |GetArray()| and |
| 140 // |PutArray()|. |
| 141 // TODO(vtl): Logically, there should be separate read checks and write |
| 142 // checks. |
| 143 // TODO(vtl): Switch more things to use this. |
| 144 void CheckArray(size_t count) const { |
| 145 internal::CheckUserPointerWithCount< |
| 146 sizeof(NonVoidType), MOJO_ALIGNOF(NonVoidType)>(pointer_, count); |
| 147 } |
| 148 |
121 // Gets the value (of type |Type|) pointed to by this user pointer. Use this | 149 // Gets the value (of type |Type|) pointed to by this user pointer. Use this |
122 // when you'd use the rvalue |*user_pointer|, but be aware that this may be | 150 // when you'd use the rvalue |*user_pointer|, but be aware that this may be |
123 // costly -- so if the value will be used multiple times, you should save it. | 151 // costly -- so if the value will be used multiple times, you should save it. |
124 // | 152 // |
125 // (We want to force a copy here, so return |Type| not |const Type&|.) | 153 // (We want to force a copy here, so return |Type| not |const Type&|.) |
126 Type Get() const { | 154 Type Get() const { |
127 internal::CheckUserPointerHelper<sizeof(Type), | 155 internal::CheckUserPointer<sizeof(Type), MOJO_ALIGNOF(Type)>(pointer_); |
128 MOJO_ALIGNOF(Type)>(pointer_); | |
129 return *pointer_; | 156 return *pointer_; |
130 } | 157 } |
131 | 158 |
132 // Gets an array (of type |Type|, or just a buffer if |Type| is |void| or | 159 // Gets an array (of type |Type|, or just a buffer if |Type| is |void| or |
133 // |const void|) of |count| elements (or bytes if |Type| is |void| or |const | 160 // |const void|) of |count| elements (or bytes if |Type| is |void| or |const |
134 // void|) from the location pointed to by this user pointer. Use this when | 161 // void|) from the location pointed to by this user pointer. Use this when |
135 // you'd do something like |memcpy(destination, user_pointer, count * | 162 // you'd do something like |memcpy(destination, user_pointer, count * |
136 // sizeof(Type)|. | 163 // sizeof(Type)|. |
137 void GetArray(typename internal::remove_const<Type>::type* destination, | 164 void GetArray(typename internal::remove_const<Type>::type* destination, |
138 size_t count) { | 165 size_t count) const { |
139 internal::CheckUserPointerWithCountHelper< | 166 internal::CheckUserPointerWithCount< |
140 sizeof(NonVoidType), MOJO_ALIGNOF(NonVoidType)>(pointer_, count); | 167 sizeof(NonVoidType), MOJO_ALIGNOF(NonVoidType)>(pointer_, count); |
141 memcpy(destination, pointer_, count * sizeof(NonVoidType)); | 168 memcpy(destination, pointer_, count * sizeof(NonVoidType)); |
142 } | 169 } |
143 | 170 |
144 // Puts a value (of type |Type|, or of type |char| if |Type| is |void|) to the | 171 // Puts a value (of type |Type|, or of type |char| if |Type| is |void|) to the |
145 // location pointed to by this user pointer. Use this when you'd use the | 172 // location pointed to by this user pointer. Use this when you'd use the |
146 // lvalue |*user_pointer|. Since this may be costly, you should avoid using | 173 // lvalue |*user_pointer|. Since this may be costly, you should avoid using |
147 // this (for the same user pointer) more than once. | 174 // this (for the same user pointer) more than once. |
148 // | 175 // |
149 // Note: This |Put()| method is not valid when |T| is const, e.g., |const | 176 // Note: This |Put()| method is not valid when |T| is const, e.g., |const |
150 // uint32_t|, but it's okay to include them so long as this template is only | 177 // uint32_t|, but it's okay to include them so long as this template is only |
151 // implicitly instantiated (see 14.7.1 of the C++11 standard) and not | 178 // implicitly instantiated (see 14.7.1 of the C++11 standard) and not |
152 // explicitly instantiated. (On implicit instantiation, only the declarations | 179 // explicitly instantiated. (On implicit instantiation, only the declarations |
153 // need be valid, not the definitions.) | 180 // need be valid, not the definitions.) |
154 // | 181 // |
155 // If |Type| is |void|, we "convert" it to |char|, so that it makes sense. | 182 // If |Type| is |void|, we "convert" it to |char|, so that it makes sense. |
156 // (Otherwise, we'd need a suitable specialization to exclude |Put()|.) | 183 // (Otherwise, we'd need a suitable specialization to exclude |Put()|.) |
157 // | 184 // |
158 // In C++11, we could do something like: | 185 // In C++11, we could do something like: |
159 // template <typename _Type = Type> | 186 // template <typename _Type = Type> |
160 // typename enable_if<!is_const<_Type>::value && | 187 // typename enable_if<!is_const<_Type>::value && |
161 // !is_void<_Type>::value>::type Put( | 188 // !is_void<_Type>::value>::type Put( |
162 // const _Type& value) { ... } | 189 // const _Type& value) { ... } |
163 // (which obviously be correct), but C++03 doesn't allow default function | 190 // (which obviously be correct), but C++03 doesn't allow default function |
164 // template arguments. | 191 // template arguments. |
165 void Put(const NonVoidType& value) { | 192 void Put(const NonVoidType& value) { |
166 internal::CheckUserPointerHelper<sizeof(NonVoidType), | 193 internal::CheckUserPointer<sizeof(NonVoidType), MOJO_ALIGNOF(NonVoidType)>( |
167 MOJO_ALIGNOF(NonVoidType)>(pointer_); | 194 pointer_); |
168 *pointer_ = value; | 195 *pointer_ = value; |
169 } | 196 } |
170 | 197 |
171 // Puts an array (of type |Type|, or just a buffer if |Type| is |void|) with | 198 // Puts an array (of type |Type|, or just a buffer if |Type| is |void|) with |
172 // |count| elements (or bytes |Type| is |void|) to the location pointed to by | 199 // |count| elements (or bytes |Type| is |void|) to the location pointed to by |
173 // this user pointer. Use this when you'd do something like | 200 // this user pointer. Use this when you'd do something like |
174 // |memcpy(user_pointer, source, count * sizeof(Type))|. | 201 // |memcpy(user_pointer, source, count * sizeof(Type))|. |
175 // | 202 // |
176 // Note: The same comments about the validity of |Put()| (except for the part | 203 // Note: The same comments about the validity of |Put()| (except for the part |
177 // about |void|) apply here. | 204 // about |void|) apply here. |
178 void PutArray(const Type* source, size_t count) { | 205 void PutArray(const Type* source, size_t count) { |
179 internal::CheckUserPointerWithCountHelper< | 206 internal::CheckUserPointerWithCount< |
180 sizeof(NonVoidType), MOJO_ALIGNOF(NonVoidType)>(pointer_, count); | 207 sizeof(NonVoidType), MOJO_ALIGNOF(NonVoidType)>(pointer_, count); |
181 memcpy(pointer_, source, count * sizeof(NonVoidType)); | 208 memcpy(pointer_, source, count * sizeof(NonVoidType)); |
182 } | 209 } |
183 | 210 |
184 // Gets a |UserPointer| at offset |i| (in |Type|s) relative to this. | 211 // Gets a |UserPointer| at offset |i| (in |Type|s) relative to this. |
185 UserPointer At(size_t i) const { | 212 UserPointer At(size_t i) const { |
186 return UserPointer(static_cast<Type*>( | 213 return UserPointer(static_cast<Type*>( |
187 static_cast<NonVoidType*>(pointer_) + i)); | 214 static_cast<NonVoidType*>(pointer_) + i)); |
188 } | 215 } |
189 | 216 |
190 // TODO(vtl): This is temporary. Get rid of this. (We should pass | |
191 // |UserPointer<>|s along appropriately, or access data in a safe way | |
192 // everywhere.) | |
193 Type* GetPointerUnsafe() const { | |
194 return pointer_; | |
195 } | |
196 | |
197 // These provides safe (read-only/write-only/read-and-write) access to a | 217 // These provides safe (read-only/write-only/read-and-write) access to a |
198 // |UserPointer<Type>| (probably pointing to an array) using just an ordinary | 218 // |UserPointer<Type>| (probably pointing to an array) using just an ordinary |
199 // pointer (obtained via |GetPointer()|). | 219 // pointer (obtained via |GetPointer()|). |
200 // | 220 // |
201 // The memory returned by |GetPointer()| may be a copy of the original user | 221 // The memory returned by |GetPointer()| may be a copy of the original user |
202 // memory, but should be modified only if the user is intended to eventually | 222 // memory, but should be modified only if the user is intended to eventually |
203 // see the change.) If any changes are made, |Commit()| should be called to | 223 // see the change.) If any changes are made, |Commit()| should be called to |
204 // guarantee that the changes are written back to user memory (it may be | 224 // guarantee that the changes are written back to user memory (it may be |
205 // called multiple times). | 225 // called multiple times). |
206 // | 226 // |
(...skipping 19 matching lines...) Expand all Loading... |
226 // } | 246 // } |
227 // | 247 // |
228 // TODO(vtl): Possibly, since we're not really being safe, we should just not | 248 // TODO(vtl): Possibly, since we're not really being safe, we should just not |
229 // copy for Release builds. | 249 // copy for Release builds. |
230 typedef UserPointerReader<Type> Reader; | 250 typedef UserPointerReader<Type> Reader; |
231 typedef UserPointerWriter<Type> Writer; | 251 typedef UserPointerWriter<Type> Writer; |
232 typedef UserPointerReaderWriter<Type> ReaderWriter; | 252 typedef UserPointerReaderWriter<Type> ReaderWriter; |
233 | 253 |
234 private: | 254 private: |
235 friend class UserPointerReader<Type>; | 255 friend class UserPointerReader<Type>; |
| 256 friend class UserPointerReader<const Type>; |
236 friend class UserPointerWriter<Type>; | 257 friend class UserPointerWriter<Type>; |
237 friend class UserPointerReaderWriter<Type>; | 258 friend class UserPointerReaderWriter<Type>; |
| 259 template <class Options> friend class UserOptionsReader; |
238 | 260 |
239 Type* pointer_; | 261 Type* pointer_; |
240 // Allow copy and assignment. | 262 // Allow copy and assignment. |
241 }; | 263 }; |
242 | 264 |
243 // Provides a convenient way to make a |UserPointer<Type>|. | 265 // Provides a convenient way to make a |UserPointer<Type>|. |
244 template <typename Type> | 266 template <typename Type> |
245 inline UserPointer<Type> MakeUserPointer(Type* pointer) { | 267 inline UserPointer<Type> MakeUserPointer(Type* pointer) { |
246 return UserPointer<Type>(pointer); | 268 return UserPointer<Type>(pointer); |
247 } | 269 } |
248 | 270 |
249 // Implementation of |UserPointer<Type>::Reader|. | 271 // Implementation of |UserPointer<Type>::Reader|. |
250 template <typename Type> | 272 template <typename Type> |
251 class UserPointerReader { | 273 class UserPointerReader { |
252 private: | 274 private: |
253 typedef typename internal::remove_const<Type>::type TypeNoConst; | 275 typedef typename internal::remove_const<Type>::type TypeNoConst; |
254 | 276 |
255 public: | 277 public: |
| 278 // Note: If |count| is zero, |GetPointer()| will always return null. |
256 UserPointerReader(UserPointer<const Type> user_pointer, size_t count) { | 279 UserPointerReader(UserPointer<const Type> user_pointer, size_t count) { |
257 Init(user_pointer.pointer_, count); | 280 Init(user_pointer.pointer_, count, true); |
258 } | 281 } |
259 UserPointerReader(UserPointer<TypeNoConst> user_pointer, size_t count) { | 282 UserPointerReader(UserPointer<TypeNoConst> user_pointer, size_t count) { |
260 Init(user_pointer.pointer_, count); | 283 Init(user_pointer.pointer_, count, true); |
261 } | 284 } |
262 | 285 |
263 const Type* GetPointer() const { return buffer_.get(); } | 286 const Type* GetPointer() const { return buffer_.get(); } |
264 | 287 |
265 private: | 288 private: |
266 void Init(const Type* user_pointer, size_t count) { | 289 template <class Options> friend class UserOptionsReader; |
267 internal::CheckUserPointerWithCountHelper< | 290 |
268 sizeof(Type), MOJO_ALIGNOF(Type)>(user_pointer, count); | 291 struct NoCheck {}; |
| 292 UserPointerReader(NoCheck, |
| 293 UserPointer<const Type> user_pointer, |
| 294 size_t count) { |
| 295 Init(user_pointer.pointer_, count, false); |
| 296 } |
| 297 |
| 298 void Init(const Type* user_pointer, size_t count, bool check) { |
| 299 if (count == 0) |
| 300 return; |
| 301 |
| 302 if (check) { |
| 303 internal::CheckUserPointerWithCount<sizeof(Type), MOJO_ALIGNOF(Type)>( |
| 304 user_pointer, count); |
| 305 } |
269 buffer_.reset(new TypeNoConst[count]); | 306 buffer_.reset(new TypeNoConst[count]); |
270 memcpy(buffer_.get(), user_pointer, count * sizeof(Type)); | 307 memcpy(buffer_.get(), user_pointer, count * sizeof(Type)); |
271 } | 308 } |
272 | 309 |
273 scoped_ptr<TypeNoConst[]> buffer_; | 310 scoped_ptr<TypeNoConst[]> buffer_; |
274 | 311 |
275 DISALLOW_COPY_AND_ASSIGN(UserPointerReader); | 312 DISALLOW_COPY_AND_ASSIGN(UserPointerReader); |
276 }; | 313 }; |
277 | 314 |
278 // Implementation of |UserPointer<Type>::Writer|. | 315 // Implementation of |UserPointer<Type>::Writer|. |
279 template <typename Type> | 316 template <typename Type> |
280 class UserPointerWriter { | 317 class UserPointerWriter { |
281 public: | 318 public: |
| 319 // Note: If |count| is zero, |GetPointer()| will always return null. |
282 UserPointerWriter(UserPointer<Type> user_pointer, size_t count) | 320 UserPointerWriter(UserPointer<Type> user_pointer, size_t count) |
283 : user_pointer_(user_pointer), | 321 : user_pointer_(user_pointer), |
284 count_(count) { | 322 count_(count) { |
285 buffer_.reset(new Type[count_]); | 323 if (count_ > 0) { |
286 memset(buffer_.get(), 0, count_ * sizeof(Type)); | 324 buffer_.reset(new Type[count_]); |
| 325 memset(buffer_.get(), 0, count_ * sizeof(Type)); |
| 326 } |
287 } | 327 } |
288 | 328 |
289 Type* GetPointer() const { return buffer_.get(); } | 329 Type* GetPointer() const { return buffer_.get(); } |
290 | 330 |
291 void Commit() { | 331 void Commit() { |
292 internal::CheckUserPointerWithCountHelper< | 332 internal::CheckUserPointerWithCount<sizeof(Type), MOJO_ALIGNOF(Type)>( |
293 sizeof(Type), MOJO_ALIGNOF(Type)>(user_pointer_.pointer_, count_); | 333 user_pointer_.pointer_, count_); |
294 memcpy(user_pointer_.pointer_, buffer_.get(), count_ * sizeof(Type)); | 334 memcpy(user_pointer_.pointer_, buffer_.get(), count_ * sizeof(Type)); |
295 } | 335 } |
296 | 336 |
297 private: | 337 private: |
298 UserPointer<Type> user_pointer_; | 338 UserPointer<Type> user_pointer_; |
299 size_t count_; | 339 size_t count_; |
300 scoped_ptr<Type[]> buffer_; | 340 scoped_ptr<Type[]> buffer_; |
301 | 341 |
302 DISALLOW_COPY_AND_ASSIGN(UserPointerWriter); | 342 DISALLOW_COPY_AND_ASSIGN(UserPointerWriter); |
303 }; | 343 }; |
304 | 344 |
305 // Implementation of |UserPointer<Type>::ReaderWriter|. | 345 // Implementation of |UserPointer<Type>::ReaderWriter|. |
306 template <typename Type> | 346 template <typename Type> |
307 class UserPointerReaderWriter { | 347 class UserPointerReaderWriter { |
308 public: | 348 public: |
| 349 // Note: If |count| is zero, |GetPointer()| will always return null. |
309 UserPointerReaderWriter(UserPointer<Type> user_pointer, size_t count) | 350 UserPointerReaderWriter(UserPointer<Type> user_pointer, size_t count) |
310 : user_pointer_(user_pointer), | 351 : user_pointer_(user_pointer), |
311 count_(count) { | 352 count_(count) { |
312 internal::CheckUserPointerWithCountHelper< | 353 if (count_ > 0) { |
313 sizeof(Type), MOJO_ALIGNOF(Type)>(user_pointer_.pointer_, count_); | 354 internal::CheckUserPointerWithCount<sizeof(Type), MOJO_ALIGNOF(Type)>( |
314 buffer_.reset(new Type[count]); | 355 user_pointer_.pointer_, count_); |
315 memcpy(buffer_.get(), user_pointer.pointer_, count * sizeof(Type)); | 356 buffer_.reset(new Type[count]); |
| 357 memcpy(buffer_.get(), user_pointer.pointer_, count * sizeof(Type)); |
| 358 } |
316 } | 359 } |
317 | 360 |
318 Type* GetPointer() const { return buffer_.get(); } | 361 Type* GetPointer() const { return buffer_.get(); } |
319 size_t GetCount() const { return count_; } | 362 size_t GetCount() const { return count_; } |
320 | 363 |
321 void Commit() { | 364 void Commit() { |
322 internal::CheckUserPointerWithCountHelper< | 365 internal::CheckUserPointerWithCount<sizeof(Type), MOJO_ALIGNOF(Type)>( |
323 sizeof(Type), MOJO_ALIGNOF(Type)>(user_pointer_.pointer_, count_); | 366 user_pointer_.pointer_, count_); |
324 memcpy(user_pointer_.pointer_, buffer_.get(), count_ * sizeof(Type)); | 367 memcpy(user_pointer_.pointer_, buffer_.get(), count_ * sizeof(Type)); |
325 } | 368 } |
326 | 369 |
327 private: | 370 private: |
328 UserPointer<Type> user_pointer_; | 371 UserPointer<Type> user_pointer_; |
329 size_t count_; | 372 size_t count_; |
330 scoped_ptr<Type[]> buffer_; | 373 scoped_ptr<Type[]> buffer_; |
331 | 374 |
332 DISALLOW_COPY_AND_ASSIGN(UserPointerReaderWriter); | 375 DISALLOW_COPY_AND_ASSIGN(UserPointerReaderWriter); |
333 }; | 376 }; |
(...skipping 22 matching lines...) Expand all Loading... |
356 // Provides a convenient way to make a |UserPointerValue<Type>|. | 399 // Provides a convenient way to make a |UserPointerValue<Type>|. |
357 template <typename Type> | 400 template <typename Type> |
358 inline UserPointerValue<Type> MakeUserPointerValue(Type* pointer) { | 401 inline UserPointerValue<Type> MakeUserPointerValue(Type* pointer) { |
359 return UserPointerValue<Type>(pointer); | 402 return UserPointerValue<Type>(pointer); |
360 } | 403 } |
361 | 404 |
362 } // namespace system | 405 } // namespace system |
363 } // namespace mojo | 406 } // namespace mojo |
364 | 407 |
365 #endif // MOJO_SYSTEM_MEMORY_H_ | 408 #endif // MOJO_SYSTEM_MEMORY_H_ |
OLD | NEW |