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_PUBLIC_CPP_BINDINGS_LIB_ARRAY_INTERNAL_H_ | 5 #ifndef MOJO_PUBLIC_CPP_BINDINGS_LIB_ARRAY_INTERNAL_H_ |
6 #define MOJO_PUBLIC_CPP_BINDINGS_LIB_ARRAY_INTERNAL_H_ | 6 #define MOJO_PUBLIC_CPP_BINDINGS_LIB_ARRAY_INTERNAL_H_ |
7 | 7 |
8 #include <new> | 8 #include <new> |
9 #include <vector> | 9 #include <vector> |
10 | 10 |
11 #include "mojo/public/cpp/bindings/lib/bindings_internal.h" | 11 #include "mojo/public/cpp/bindings/lib/bindings_internal.h" |
12 #include "mojo/public/cpp/bindings/lib/bindings_serialization.h" | 12 #include "mojo/public/cpp/bindings/lib/bindings_serialization.h" |
13 #include "mojo/public/cpp/bindings/lib/bounds_checker.h" | 13 #include "mojo/public/cpp/bindings/lib/bounds_checker.h" |
14 #include "mojo/public/cpp/bindings/lib/buffer.h" | 14 #include "mojo/public/cpp/bindings/lib/buffer.h" |
| 15 #include "mojo/public/cpp/bindings/lib/validation_errors.h" |
15 | 16 |
16 namespace mojo { | 17 namespace mojo { |
17 template <typename T> class Array; | 18 template <typename T> class Array; |
18 class String; | 19 class String; |
19 | 20 |
20 namespace internal { | 21 namespace internal { |
21 | 22 |
22 template <typename T> | 23 template <typename T> |
23 struct ArrayDataTraits { | 24 struct ArrayDataTraits { |
24 typedef T StorageType; | 25 typedef T StorageType; |
(...skipping 151 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
176 ElementType* elements, | 177 ElementType* elements, |
177 std::vector<Handle>* handles) { | 178 std::vector<Handle>* handles) { |
178 for (uint32_t i = 0; i < header->num_elements; ++i) | 179 for (uint32_t i = 0; i < header->num_elements; ++i) |
179 Decode(&elements[i], handles); | 180 Decode(&elements[i], handles); |
180 } | 181 } |
181 | 182 |
182 static bool ValidateElements(const ArrayHeader* header, | 183 static bool ValidateElements(const ArrayHeader* header, |
183 const ElementType* elements, | 184 const ElementType* elements, |
184 BoundsChecker* bounds_checker) { | 185 BoundsChecker* bounds_checker) { |
185 for (uint32_t i = 0; i < header->num_elements; ++i) { | 186 for (uint32_t i = 0; i < header->num_elements; ++i) { |
186 if (!ValidateEncodedPointer(&elements[i].offset) || | 187 if (!ValidateEncodedPointer(&elements[i].offset)) { |
187 !P::Validate(DecodePointerRaw(&elements[i].offset), bounds_checker)) { | 188 ReportValidationError(VALIDATION_ERROR_ILLEGAL_POINTER); |
188 return false; | 189 return false; |
189 } | 190 } |
| 191 if (!P::Validate(DecodePointerRaw(&elements[i].offset), bounds_checker)) |
| 192 return false; |
190 } | 193 } |
191 return true; | 194 return true; |
192 } | 195 } |
193 }; | 196 }; |
194 | 197 |
195 template <typename T> | 198 template <typename T> |
196 class Array_Data { | 199 class Array_Data { |
197 public: | 200 public: |
198 typedef ArrayDataTraits<T> Traits; | 201 typedef ArrayDataTraits<T> Traits; |
199 typedef typename Traits::StorageType StorageType; | 202 typedef typename Traits::StorageType StorageType; |
200 typedef typename Traits::Ref Ref; | 203 typedef typename Traits::Ref Ref; |
201 typedef typename Traits::ConstRef ConstRef; | 204 typedef typename Traits::ConstRef ConstRef; |
202 typedef ArraySerializationHelper<T, IsHandle<T>::value> Helper; | 205 typedef ArraySerializationHelper<T, IsHandle<T>::value> Helper; |
203 | 206 |
204 static Array_Data<T>* New(size_t num_elements, Buffer* buf) { | 207 static Array_Data<T>* New(size_t num_elements, Buffer* buf) { |
205 size_t num_bytes = sizeof(Array_Data<T>) + | 208 size_t num_bytes = sizeof(Array_Data<T>) + |
206 Traits::GetStorageSize(num_elements); | 209 Traits::GetStorageSize(num_elements); |
207 return new (buf->Allocate(num_bytes)) Array_Data<T>(num_bytes, | 210 return new (buf->Allocate(num_bytes)) Array_Data<T>(num_bytes, |
208 num_elements); | 211 num_elements); |
209 } | 212 } |
210 | 213 |
211 static bool Validate(const void* data, BoundsChecker* bounds_checker) { | 214 static bool Validate(const void* data, BoundsChecker* bounds_checker) { |
212 if (!data) | 215 if (!data) |
213 return true; | 216 return true; |
214 if (!IsAligned(data)) | 217 if (!IsAligned(data)) { |
| 218 ReportValidationError(VALIDATION_ERROR_MISALIGNED_OBJECT); |
215 return false; | 219 return false; |
216 if (!bounds_checker->IsValidRange(data, sizeof(ArrayHeader))) | 220 } |
| 221 if (!bounds_checker->IsValidRange(data, sizeof(ArrayHeader))) { |
| 222 ReportValidationError(VALIDATION_ERROR_ILLEGAL_MEMORY_RANGE); |
217 return false; | 223 return false; |
| 224 } |
218 const ArrayHeader* header = static_cast<const ArrayHeader*>(data); | 225 const ArrayHeader* header = static_cast<const ArrayHeader*>(data); |
219 if (header->num_bytes < (sizeof(Array_Data<T>) + | 226 if (header->num_bytes < (sizeof(Array_Data<T>) + |
220 Traits::GetStorageSize(header->num_elements))) { | 227 Traits::GetStorageSize(header->num_elements))) { |
| 228 ReportValidationError(VALIDATION_ERROR_UNEXPECTED_ARRAY_HEADER); |
221 return false; | 229 return false; |
222 } | 230 } |
223 if (!bounds_checker->ClaimMemory(data, header->num_bytes)) | 231 if (!bounds_checker->ClaimMemory(data, header->num_bytes)) { |
| 232 ReportValidationError(VALIDATION_ERROR_ILLEGAL_MEMORY_RANGE); |
224 return false; | 233 return false; |
| 234 } |
225 | 235 |
226 const Array_Data<T>* object = static_cast<const Array_Data<T>*>(data); | 236 const Array_Data<T>* object = static_cast<const Array_Data<T>*>(data); |
227 return Helper::ValidateElements(&object->header_, object->storage(), | 237 return Helper::ValidateElements(&object->header_, object->storage(), |
228 bounds_checker); | 238 bounds_checker); |
229 } | 239 } |
230 | 240 |
231 size_t size() const { return header_.num_elements; } | 241 size_t size() const { return header_.num_elements; } |
232 | 242 |
233 Ref at(size_t offset) { | 243 Ref at(size_t offset) { |
234 assert(offset < static_cast<size_t>(header_.num_elements)); | 244 assert(offset < static_cast<size_t>(header_.num_elements)); |
(...skipping 81 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
316 }; | 326 }; |
317 | 327 |
318 template <> struct WrapperTraits<String, false> { | 328 template <> struct WrapperTraits<String, false> { |
319 typedef String_Data* DataType; | 329 typedef String_Data* DataType; |
320 }; | 330 }; |
321 | 331 |
322 } // namespace internal | 332 } // namespace internal |
323 } // namespace mojo | 333 } // namespace mojo |
324 | 334 |
325 #endif // MOJO_PUBLIC_CPP_BINDINGS_LIB_ARRAY_INTERNAL_H_ | 335 #endif // MOJO_PUBLIC_CPP_BINDINGS_LIB_ARRAY_INTERNAL_H_ |
OLD | NEW |