1 /* 2 * Copyright (C) 2015 The Android Open Source Project 3 * 4 * Licensed under the Apache License, Version 2.0 (the "License"); 5 * you may not use this file except in compliance with the License. 6 * You may obtain a copy of the License at 7 * 8 * http://www.apache.org/licenses/LICENSE-2.0 9 * 10 * Unless required by applicable law or agreed to in writing, software 11 * distributed under the License is distributed on an "AS IS" BASIS, 12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13 * See the License for the specific language governing permissions and 14 * limitations under the License. 15 */ 16 17 #ifndef BERBERIS_BASE_STRUCT_CHECK_H_ 18 #define BERBERIS_BASE_STRUCT_CHECK_H_ 19 20 #include <climits> // CHAR_BIT 21 #include <cstddef> 22 23 namespace berberis { 24 25 // Helper macroses for verification purposes. When we declare a data structure 26 // with forced align we want to verify that size and offset of the resulting 27 // structure is now the same as for structure which we want to mimic. 28 #define CHECK_STRUCT_LAYOUT(type, size, align) \ 29 static_assert(sizeof(type) * CHAR_BIT == size, \ 30 "size of " #type " must be " #size " bit because it's " #size " bit on guest"); \ 31 static_assert(alignof(type) * CHAR_BIT == align, \ 32 "align of " #type " must be " #align " bit because it's " #align " bit on guest") 33 34 // If structure is allocated on guest and used by host then we could declare them "partially 35 // compatible" if alignment requirements on host are less strict than on guest. 36 #define CHECK_STRUCT_LAYOUT_GUEST_TO_HOST(type, size, align) \ 37 static_assert(sizeof(type) * CHAR_BIT == size, \ 38 "size of " #type " must be " #size " bit because it's " #size " bit on guest"); \ 39 static_assert(alignof(type) * CHAR_BIT <= align && align % (alignof(type) * CHAR_BIT) == 0, \ 40 "align of " #type " must be less or equal to " #align " bit because it's " #align \ 41 " bit on guest") 42 43 // If structure is allocated on host and used by guest then we could declare them "partially 44 // compatible" if alignment requirements on guest are less strict than on host. 45 #define CHECK_STRUCT_LAYOUT_HOST_TO_GUEST(type, size, align) \ 46 static_assert(sizeof(type) * CHAR_BIT == size, \ 47 "size of " #type " must be " #size " bit because it's " #size " bit on guest"); \ 48 static_assert(alignof(type) * CHAR_BIT >= align && (alignof(type) * CHAR_BIT) % align == 0, \ 49 "align of " #type " must be more or equal to " #align " bit because it's " #align \ 50 " bit on guest") 51 52 #define CHECK_FIELD_LAYOUT(type, field, offset, size) \ 53 static_assert(offsetof(type, field) * CHAR_BIT == offset, \ 54 "offset of `" #field "' field in " #type " must be " #offset \ 55 " because it's " #offset " on guest"); \ 56 static_assert(sizeof(static_cast<type*>(nullptr)->field) * CHAR_BIT == size, \ 57 "size of `" #field "' field in " #type " must be " #size \ 58 " bit because it's " #size " bit on guest") 59 60 } // namespace berberis 61 62 #endif // BERBERIS_BASE_STRUCT_CHECK_H_ 63