| OLD | NEW |
| (Empty) |
| 1 // Copyright 2016 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 #include <mojo/bindings/union.h> | |
| 6 | |
| 7 #include <assert.h> | |
| 8 #include <mojo/bindings/internal/type_descriptor.h> | |
| 9 #include <string.h> | |
| 10 | |
| 11 #define UNION_TAG_UNKNOWN ((uint32_t)0xFFFFFFFF) | |
| 12 | |
| 13 size_t MojomUnion_ComputeSerializedSize( | |
| 14 const struct MojomTypeDescriptorUnion* in_type_desc, | |
| 15 const struct MojomUnionLayout* in_union_data) { | |
| 16 assert(in_type_desc); | |
| 17 assert(in_union_data); | |
| 18 | |
| 19 for (size_t i = 0; i < in_type_desc->num_entries; i++) { | |
| 20 const struct MojomTypeDescriptorUnionEntry* entry = | |
| 21 &(in_type_desc->entries[i]); | |
| 22 if (in_union_data->tag != entry->tag) | |
| 23 continue; | |
| 24 | |
| 25 // We should skip non-pointer types. | |
| 26 if (!MojomType_IsPointer(entry->elem_type)) | |
| 27 break; | |
| 28 | |
| 29 return MojomType_DispatchComputeSerializedSize( | |
| 30 entry->elem_type, entry->elem_descriptor, entry->nullable, | |
| 31 &(in_union_data->data.pointer.ptr)); | |
| 32 } | |
| 33 return 0; | |
| 34 } | |
| 35 | |
| 36 void MojomUnion_EncodePointersAndHandles( | |
| 37 const struct MojomTypeDescriptorUnion* in_type_desc, | |
| 38 struct MojomUnionLayout* inout_union, | |
| 39 uint32_t in_buf_size, | |
| 40 struct MojomHandleBuffer* inout_handles_buffer) { | |
| 41 assert(in_buf_size >= sizeof(struct MojomUnionLayout)); | |
| 42 | |
| 43 for (size_t i = 0; i < in_type_desc->num_entries; i++) { | |
| 44 const struct MojomTypeDescriptorUnionEntry* entry = | |
| 45 &(in_type_desc->entries[i]); | |
| 46 | |
| 47 if (inout_union->tag != entry->tag) | |
| 48 continue; | |
| 49 | |
| 50 if (entry->elem_type == MOJOM_TYPE_DESCRIPTOR_TYPE_POD) | |
| 51 break; | |
| 52 | |
| 53 MojomType_DispatchEncodePointersAndHandles( | |
| 54 entry->elem_type, | |
| 55 entry->elem_descriptor, | |
| 56 entry->nullable, | |
| 57 &inout_union->data, | |
| 58 in_buf_size - ((char*)&inout_union->data - (char*)inout_union), | |
| 59 inout_handles_buffer); | |
| 60 | |
| 61 break; | |
| 62 } | |
| 63 } | |
| 64 | |
| 65 void MojomUnion_DecodePointersAndHandles( | |
| 66 const struct MojomTypeDescriptorUnion* in_type_desc, | |
| 67 struct MojomUnionLayout* inout_union, | |
| 68 uint32_t in_union_size, | |
| 69 MojoHandle* inout_handles, | |
| 70 uint32_t in_num_handles) { | |
| 71 assert(in_union_size >= sizeof(struct MojomUnionLayout)); | |
| 72 assert(inout_handles != NULL || in_num_handles == 0); | |
| 73 | |
| 74 for (size_t i = 0; i < in_type_desc->num_entries; i++) { | |
| 75 const struct MojomTypeDescriptorUnionEntry* entry = | |
| 76 &(in_type_desc->entries[i]); | |
| 77 | |
| 78 if (inout_union->tag != entry->tag) | |
| 79 continue; | |
| 80 | |
| 81 if (entry->elem_type == MOJOM_TYPE_DESCRIPTOR_TYPE_POD) | |
| 82 break; | |
| 83 | |
| 84 MojomType_DispatchDecodePointersAndHandles( | |
| 85 entry->elem_type, | |
| 86 entry->elem_descriptor, | |
| 87 entry->nullable, | |
| 88 &inout_union->data, | |
| 89 in_union_size - ((char*)&inout_union->data - (char*)inout_union), | |
| 90 inout_handles, | |
| 91 in_num_handles); | |
| 92 | |
| 93 break; | |
| 94 } | |
| 95 } | |
| 96 | |
| 97 MojomValidationResult MojomUnion_Validate( | |
| 98 const struct MojomTypeDescriptorUnion* in_type_desc, | |
| 99 bool in_nullable, | |
| 100 const struct MojomUnionLayout* in_union, | |
| 101 uint32_t in_union_size, | |
| 102 uint32_t in_num_handles, | |
| 103 struct MojomValidationContext* inout_context) { | |
| 104 for (size_t i = 0; i < in_type_desc->num_entries; i++) { | |
| 105 const struct MojomTypeDescriptorUnionEntry* entry = | |
| 106 &(in_type_desc->entries[i]); | |
| 107 | |
| 108 if (in_union->tag != entry->tag) | |
| 109 continue; | |
| 110 | |
| 111 if (entry->elem_type == MOJOM_TYPE_DESCRIPTOR_TYPE_POD) | |
| 112 break; | |
| 113 | |
| 114 if (!in_nullable && in_union->size != sizeof(struct MojomUnionLayout)) | |
| 115 return MOJOM_VALIDATION_UNEXPECTED_NULL_UNION; | |
| 116 | |
| 117 return MojomType_DispatchValidate( | |
| 118 entry->elem_type, | |
| 119 entry->elem_descriptor, | |
| 120 entry->nullable, | |
| 121 &(in_union->data), | |
| 122 in_union_size - ((char*)&(in_union->data) - (char*)in_union), | |
| 123 in_num_handles, | |
| 124 inout_context); | |
| 125 } | |
| 126 return MOJOM_VALIDATION_ERROR_NONE; | |
| 127 } | |
| 128 | |
| 129 bool MojomUnion_DeepCopy(struct MojomBuffer* buffer, | |
| 130 const struct MojomTypeDescriptorUnion* in_type_desc, | |
| 131 const struct MojomUnionLayout* in_union_data, | |
| 132 struct MojomUnionLayout* out_union_data) { | |
| 133 memcpy(out_union_data, in_union_data, sizeof(struct MojomUnionLayout)); | |
| 134 | |
| 135 // Unions with size 0 are null. | |
| 136 if (in_union_data->size == 0) | |
| 137 return true; | |
| 138 | |
| 139 for (size_t i = 0; i < in_type_desc->num_entries; i++) { | |
| 140 const struct MojomTypeDescriptorUnionEntry* entry = | |
| 141 &(in_type_desc->entries[i]); | |
| 142 if (in_union_data->tag != entry->tag) | |
| 143 continue; | |
| 144 | |
| 145 // We should skip non-pointer types. | |
| 146 if (entry->elem_type == MOJOM_TYPE_DESCRIPTOR_TYPE_POD) | |
| 147 return true; | |
| 148 | |
| 149 return MojomType_DispatchDeepCopy( | |
| 150 buffer, entry->elem_type, entry->elem_descriptor, | |
| 151 &(in_union_data->data), &(out_union_data->data)); | |
| 152 } | |
| 153 // We reach here if we don't recognize the tag. If it's the UNKNOWN tag, it's | |
| 154 // not a failure. If it's an unrecognized tag (erroneous or because this union | |
| 155 // is from a future-version), we don't know how to copy it, so the copy is a | |
| 156 // failure. | |
| 157 return in_union_data->tag < in_type_desc->num_fields || | |
| 158 in_union_data->tag == UNION_TAG_UNKNOWN; | |
| 159 } | |
| OLD | NEW |