Home | History | Annotate | Download | only in lib
      1 // Copyright 2015 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_UTIL_H_
      6 #define MOJO_PUBLIC_CPP_BINDINGS_LIB_VALIDATION_UTIL_H_
      7 
      8 #include <stdint.h>
      9 
     10 #include "mojo/public/cpp/bindings/lib/bindings_internal.h"
     11 #include "mojo/public/cpp/bindings/lib/serialization_util.h"
     12 #include "mojo/public/cpp/bindings/lib/validate_params.h"
     13 #include "mojo/public/cpp/bindings/lib/validation_context.h"
     14 #include "mojo/public/cpp/bindings/lib/validation_errors.h"
     15 #include "mojo/public/cpp/bindings/message.h"
     16 
     17 namespace mojo {
     18 namespace internal {
     19 
     20 // Checks whether decoding the pointer will overflow and produce a pointer
     21 // smaller than |offset|.
     22 bool ValidateEncodedPointer(const uint64_t* offset);
     23 
     24 template <typename T>
     25 bool ValidatePointer(const Pointer<T>& input,
     26                      ValidationContext* validation_context) {
     27   bool result = ValidateEncodedPointer(&input.offset);
     28   if (!result)
     29     ReportValidationError(validation_context, VALIDATION_ERROR_ILLEGAL_POINTER);
     30 
     31   return result;
     32 }
     33 
     34 // Validates that |data| contains a valid struct header, in terms of alignment
     35 // and size (i.e., the |num_bytes| field of the header is sufficient for storing
     36 // the header itself). Besides, it checks that the memory range
     37 // [data, data + num_bytes) is not marked as occupied by other objects in
     38 // |validation_context|. On success, the memory range is marked as occupied.
     39 // Note: Does not verify |version| or that |num_bytes| is correct for the
     40 // claimed version.
     41 bool ValidateStructHeaderAndClaimMemory(const void* data,
     42                                         ValidationContext* validation_context);
     43 
     44 // Validates that |data| contains a valid union header, in terms of alignment
     45 // and size. If not inlined, it checks that the memory range
     46 // [data, data + num_bytes) is not marked as occupied by other objects in
     47 // |validation_context|. On success, the memory range is marked as occupied.
     48 bool ValidateUnionHeaderAndClaimMemory(const void* data,
     49                                        bool inlined,
     50                                        ValidationContext* validation_context);
     51 
     52 // Validates that the message is a request which doesn't expect a response.
     53 bool ValidateMessageIsRequestWithoutResponse(
     54     const Message* message,
     55     ValidationContext* validation_context);
     56 
     57 // Validates that the message is a request expecting a response.
     58 bool ValidateMessageIsRequestExpectingResponse(
     59     const Message* message,
     60     ValidationContext* validation_context);
     61 
     62 // Validates that the message is a response.
     63 bool ValidateMessageIsResponse(const Message* message,
     64                                ValidationContext* validation_context);
     65 
     66 // Validates that the message payload is a valid struct of type ParamsType.
     67 template <typename ParamsType>
     68 bool ValidateMessagePayload(const Message* message,
     69                             ValidationContext* validation_context) {
     70   return ParamsType::Validate(message->payload(), validation_context);
     71 }
     72 
     73 // The following methods validate control messages defined in
     74 // interface_control_messages.mojom.
     75 bool ValidateControlRequest(const Message* message,
     76                             ValidationContext* validation_context);
     77 bool ValidateControlResponse(const Message* message,
     78                              ValidationContext* validation_context);
     79 
     80 // The following Validate.*NonNullable() functions validate that the given
     81 // |input| is not null/invalid.
     82 template <typename T>
     83 bool ValidatePointerNonNullable(const T& input,
     84                                 const char* error_message,
     85                                 ValidationContext* validation_context) {
     86   if (input.offset)
     87     return true;
     88 
     89   ReportValidationError(validation_context,
     90                         VALIDATION_ERROR_UNEXPECTED_NULL_POINTER,
     91                         error_message);
     92   return false;
     93 }
     94 
     95 template <typename T>
     96 bool ValidateInlinedUnionNonNullable(const T& input,
     97                                      const char* error_message,
     98                                      ValidationContext* validation_context) {
     99   if (!input.is_null())
    100     return true;
    101 
    102   ReportValidationError(validation_context,
    103                         VALIDATION_ERROR_UNEXPECTED_NULL_POINTER,
    104                         error_message);
    105   return false;
    106 }
    107 
    108 bool IsHandleOrInterfaceValid(const AssociatedInterface_Data& input);
    109 bool IsHandleOrInterfaceValid(const AssociatedInterfaceRequest_Data& input);
    110 bool IsHandleOrInterfaceValid(const Interface_Data& input);
    111 bool IsHandleOrInterfaceValid(const Handle_Data& input);
    112 
    113 bool ValidateHandleOrInterfaceNonNullable(
    114     const AssociatedInterface_Data& input,
    115     const char* error_message,
    116     ValidationContext* validation_context);
    117 bool ValidateHandleOrInterfaceNonNullable(
    118     const AssociatedInterfaceRequest_Data& input,
    119     const char* error_message,
    120     ValidationContext* validation_context);
    121 bool ValidateHandleOrInterfaceNonNullable(
    122     const Interface_Data& input,
    123     const char* error_message,
    124     ValidationContext* validation_context);
    125 bool ValidateHandleOrInterfaceNonNullable(
    126     const Handle_Data& input,
    127     const char* error_message,
    128     ValidationContext* validation_context);
    129 
    130 template <typename T>
    131 bool ValidateContainer(const Pointer<T>& input,
    132                        ValidationContext* validation_context,
    133                        const ContainerValidateParams* validate_params) {
    134   return ValidatePointer(input, validation_context) &&
    135          T::Validate(input.Get(), validation_context, validate_params);
    136 }
    137 
    138 template <typename T>
    139 bool ValidateStruct(const Pointer<T>& input,
    140                     ValidationContext* validation_context) {
    141   return ValidatePointer(input, validation_context) &&
    142          T::Validate(input.Get(), validation_context);
    143 }
    144 
    145 template <typename T>
    146 bool ValidateInlinedUnion(const T& input,
    147                           ValidationContext* validation_context) {
    148   return T::Validate(&input, validation_context, true);
    149 }
    150 
    151 template <typename T>
    152 bool ValidateNonInlinedUnion(const Pointer<T>& input,
    153                              ValidationContext* validation_context) {
    154   return ValidatePointer(input, validation_context) &&
    155          T::Validate(input.Get(), validation_context, false);
    156 }
    157 
    158 bool ValidateHandleOrInterface(const AssociatedInterface_Data& input,
    159                                ValidationContext* validation_context);
    160 bool ValidateHandleOrInterface(const AssociatedInterfaceRequest_Data& input,
    161                                ValidationContext* validation_context);
    162 bool ValidateHandleOrInterface(const Interface_Data& input,
    163                                ValidationContext* validation_context);
    164 bool ValidateHandleOrInterface(const Handle_Data& input,
    165                                ValidationContext* validation_context);
    166 
    167 }  // namespace internal
    168 }  // namespace mojo
    169 
    170 #endif  // MOJO_PUBLIC_CPP_BINDINGS_LIB_VALIDATION_UTIL_H_
    171