• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // Copyright 2014 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
4 
5 #ifndef MOJO_PUBLIC_CPP_BINDINGS_LIB_VALIDATION_ERRORS_H_
6 #define MOJO_PUBLIC_CPP_BINDINGS_LIB_VALIDATION_ERRORS_H_
7 
8 #include "mojo/public/cpp/system/macros.h"
9 
10 namespace mojo {
11 namespace internal {
12 
13 enum ValidationError {
14   // There is no validation error.
15   VALIDATION_ERROR_NONE,
16   // An object (struct or array) is not 8-byte aligned.
17   VALIDATION_ERROR_MISALIGNED_OBJECT,
18   // An object is not contained inside the message data, or it overlaps other
19   // objects.
20   VALIDATION_ERROR_ILLEGAL_MEMORY_RANGE,
21   // A struct header doesn't make sense, for example:
22   // - |num_bytes| is smaller than the size of the oldest version that we
23   // support.
24   // - |num_fields| is smaller than the field number of the oldest version that
25   // we support.
26   // - |num_bytes| and |num_fields| don't match.
27   VALIDATION_ERROR_UNEXPECTED_STRUCT_HEADER,
28   // An array header doesn't make sense, for example:
29   // - |num_bytes| is smaller than the size of the header plus the size required
30   // to store |num_elements| elements.
31   // - For fixed-size arrays, |num_elements| is different than the specified
32   // size.
33   VALIDATION_ERROR_UNEXPECTED_ARRAY_HEADER,
34   // An encoded handle is illegal.
35   VALIDATION_ERROR_ILLEGAL_HANDLE,
36   // A non-nullable handle field is set to invalid handle.
37   VALIDATION_ERROR_UNEXPECTED_INVALID_HANDLE,
38   // An encoded pointer is illegal.
39   VALIDATION_ERROR_ILLEGAL_POINTER,
40   // A non-nullable pointer field is set to null.
41   VALIDATION_ERROR_UNEXPECTED_NULL_POINTER,
42   // |flags| in the message header is an invalid flag combination.
43   VALIDATION_ERROR_MESSAGE_HEADER_INVALID_FLAG_COMBINATION,
44   // |flags| in the message header indicates that a request ID is required but
45   // there isn't one.
46   VALIDATION_ERROR_MESSAGE_HEADER_MISSING_REQUEST_ID,
47 };
48 
49 const char* ValidationErrorToString(ValidationError error);
50 
51 void ReportValidationError(ValidationError error,
52                            const char* description = NULL);
53 
54 // Only used by validation tests and when there is only one thread doing message
55 // validation.
56 class ValidationErrorObserverForTesting {
57  public:
58   ValidationErrorObserverForTesting();
59   ~ValidationErrorObserverForTesting();
60 
last_error()61   ValidationError last_error() const { return last_error_; }
set_last_error(ValidationError error)62   void set_last_error(ValidationError error) { last_error_ = error; }
63 
64  private:
65   ValidationError last_error_;
66 
67   MOJO_DISALLOW_COPY_AND_ASSIGN(ValidationErrorObserverForTesting);
68 };
69 
70 // Used only by MOJO_INTERNAL_DLOG_SERIALIZATION_WARNING. Don't use it directly.
71 //
72 // The function returns true if the error is recorded (by a
73 // SerializationWarningObserverForTesting object), false otherwise.
74 bool ReportSerializationWarning(ValidationError error);
75 
76 // Only used by serialization tests and when there is only one thread doing
77 // message serialization.
78 class SerializationWarningObserverForTesting {
79  public:
80   SerializationWarningObserverForTesting();
81   ~SerializationWarningObserverForTesting();
82 
last_warning()83   ValidationError last_warning() const { return last_warning_; }
set_last_warning(ValidationError error)84   void set_last_warning(ValidationError error) { last_warning_ = error; }
85 
86  private:
87   ValidationError last_warning_;
88 
89   MOJO_DISALLOW_COPY_AND_ASSIGN(SerializationWarningObserverForTesting);
90 };
91 
92 }  // namespace internal
93 }  // namespace mojo
94 
95 // In debug build, logs a serialization warning if |condition| evaluates to
96 // true:
97 //   - if there is a SerializationWarningObserverForTesting object alive,
98 //     records |error| in it;
99 //   - otherwise, logs a fatal-level message.
100 // |error| is the validation error that will be triggered by the receiver
101 // of the serialzation result.
102 //
103 // In non-debug build, does nothing (not even compiling |condition|).
104 #define MOJO_INTERNAL_DLOG_SERIALIZATION_WARNING( \
105     condition, error, description) \
106   MOJO_DLOG_IF(FATAL, (condition) && !ReportSerializationWarning(error)) \
107       << "The outgoing message will trigger " \
108       << ValidationErrorToString(error) << " at the receiving side (" \
109       << description << ").";
110 
111 #endif  // MOJO_PUBLIC_CPP_BINDINGS_LIB_VALIDATION_ERRORS_H_
112