File indexing completed on 2025-01-31 10:12:21
0001
0002
0003
0004
0005
0006
0007
0008
0009
0010
0011
0012
0013
0014
0015 #ifndef GOOGLE_PROTOBUF_GENERATED_MESSAGE_UTIL_H__
0016 #define GOOGLE_PROTOBUF_GENERATED_MESSAGE_UTIL_H__
0017
0018 #include <assert.h>
0019
0020 #include <algorithm>
0021 #include <atomic>
0022 #include <climits>
0023 #include <cstddef>
0024 #include <memory>
0025 #include <string>
0026 #include <type_traits>
0027 #include <utility>
0028 #include <vector>
0029
0030 #include "google/protobuf/stubs/common.h"
0031 #include "absl/base/call_once.h"
0032 #include "absl/base/casts.h"
0033 #include "absl/strings/string_view.h"
0034 #include "google/protobuf/any.h"
0035 #include "google/protobuf/has_bits.h"
0036 #include "google/protobuf/implicit_weak_message.h"
0037 #include "google/protobuf/message_lite.h"
0038 #include "google/protobuf/port.h"
0039 #include "google/protobuf/repeated_field.h"
0040 #include "google/protobuf/repeated_ptr_field.h"
0041 #include "google/protobuf/wire_format_lite.h"
0042
0043
0044
0045 #include "google/protobuf/port_def.inc"
0046
0047 #ifdef SWIG
0048 #error "You cannot SWIG proto headers"
0049 #endif
0050
0051 namespace google {
0052 namespace protobuf {
0053
0054 class Arena;
0055 class Message;
0056
0057 namespace io {
0058 class CodedInputStream;
0059 }
0060
0061 namespace internal {
0062
0063
0064
0065
0066
0067 PROTOBUF_EXPORT extern std::atomic<bool> init_protobuf_defaults_state;
0068 PROTOBUF_EXPORT void InitProtobufDefaultsSlow();
0069 PROTOBUF_EXPORT inline void InitProtobufDefaults() {
0070 if (PROTOBUF_PREDICT_FALSE(
0071 !init_protobuf_defaults_state.load(std::memory_order_acquire))) {
0072 InitProtobufDefaultsSlow();
0073 }
0074 }
0075
0076
0077 PROTOBUF_EXPORT inline const std::string& GetEmptyString() {
0078 InitProtobufDefaults();
0079 return GetEmptyStringAlreadyInited();
0080 }
0081
0082
0083
0084 union EmptyCord {
0085 constexpr EmptyCord() : value() {}
0086 ~EmptyCord() {}
0087 ::absl::Cord value;
0088 };
0089 PROTOBUF_EXPORT extern const EmptyCord empty_cord_;
0090
0091 constexpr const ::absl::Cord& GetEmptyCordAlreadyInited() {
0092 return empty_cord_.value;
0093 }
0094
0095
0096
0097
0098
0099
0100 template <typename Msg>
0101 bool AllAreInitialized(const RepeatedPtrField<Msg>& t) {
0102 for (int i = t.size(); --i >= 0;) {
0103 if (!t.Get(i).IsInitialized()) return false;
0104 }
0105 return true;
0106 }
0107
0108
0109
0110
0111 template <class T>
0112 bool AllAreInitializedWeak(const RepeatedPtrField<T>& t) {
0113 for (int i = t.size(); --i >= 0;) {
0114 if (!reinterpret_cast<const RepeatedPtrFieldBase&>(t)
0115 .Get<ImplicitWeakTypeHandler<T> >(i)
0116 .IsInitialized()) {
0117 return false;
0118 }
0119 }
0120 return true;
0121 }
0122
0123 inline bool IsPresent(const void* base, uint32_t hasbit) {
0124 const uint32_t* has_bits_array = static_cast<const uint32_t*>(base);
0125 return (has_bits_array[hasbit / 32] & (1u << (hasbit & 31))) != 0;
0126 }
0127
0128 inline bool IsOneofPresent(const void* base, uint32_t offset, uint32_t tag) {
0129 const uint32_t* oneof = reinterpret_cast<const uint32_t*>(
0130 static_cast<const uint8_t*>(base) + offset);
0131 return *oneof == tag >> 3;
0132 }
0133
0134 typedef void (*SpecialSerializer)(const uint8_t* base, uint32_t offset,
0135 uint32_t tag, uint32_t has_offset,
0136 io::CodedOutputStream* output);
0137
0138 PROTOBUF_EXPORT void ExtensionSerializer(const MessageLite* extendee,
0139 const uint8_t* ptr, uint32_t offset,
0140 uint32_t tag, uint32_t has_offset,
0141 io::CodedOutputStream* output);
0142 PROTOBUF_EXPORT void UnknownFieldSerializerLite(const uint8_t* base,
0143 uint32_t offset, uint32_t tag,
0144 uint32_t has_offset,
0145 io::CodedOutputStream* output);
0146
0147 PROTOBUF_EXPORT MessageLite* DuplicateIfNonNullInternal(MessageLite* message);
0148 PROTOBUF_EXPORT MessageLite* GetOwnedMessageInternal(Arena* message_arena,
0149 MessageLite* submessage,
0150 Arena* submessage_arena);
0151 PROTOBUF_EXPORT void GenericSwap(MessageLite* m1, MessageLite* m2);
0152
0153 PROTOBUF_EXPORT void GenericSwap(Message* m1, Message* m2);
0154
0155 template <typename T>
0156 T* DuplicateIfNonNull(T* message) {
0157
0158
0159 return reinterpret_cast<T*>(
0160 DuplicateIfNonNullInternal(reinterpret_cast<MessageLite*>(message)));
0161 }
0162
0163 template <typename T>
0164 T* GetOwnedMessage(Arena* message_arena, T* submessage,
0165 Arena* submessage_arena) {
0166
0167
0168 return reinterpret_cast<T*>(GetOwnedMessageInternal(
0169 message_arena, reinterpret_cast<MessageLite*>(submessage),
0170 submessage_arena));
0171 }
0172
0173 PROTOBUF_EXPORT void DestroyMessage(const void* message);
0174 PROTOBUF_EXPORT void DestroyString(const void* s);
0175
0176 inline void OnShutdownDestroyMessage(const void* ptr) {
0177 OnShutdownRun(DestroyMessage, ptr);
0178 }
0179
0180 inline void OnShutdownDestroyString(const std::string* ptr) {
0181 OnShutdownRun(DestroyString, ptr);
0182 }
0183
0184
0185
0186
0187 template <typename storage_type>
0188 struct MapSorterIt {
0189 storage_type* ptr;
0190 MapSorterIt(storage_type* ptr) : ptr(ptr) {}
0191 bool operator==(const MapSorterIt& other) const { return ptr == other.ptr; }
0192 bool operator!=(const MapSorterIt& other) const { return !(*this == other); }
0193 MapSorterIt& operator++() {
0194 ++ptr;
0195 return *this;
0196 }
0197 MapSorterIt operator++(int) {
0198 auto other = *this;
0199 ++ptr;
0200 return other;
0201 }
0202 MapSorterIt operator+(int v) { return MapSorterIt{ptr + v}; }
0203 };
0204
0205
0206 template <typename KeyT>
0207 struct MapSorterLessThan {
0208 using storage_type = std::pair<KeyT, const void*>;
0209 bool operator()(const storage_type& a, const storage_type& b) const {
0210 return a.first < b.first;
0211 }
0212 };
0213
0214
0215
0216
0217 template <typename MapT>
0218 class MapSorterFlat {
0219 public:
0220 using value_type = typename MapT::value_type;
0221
0222
0223
0224 using storage_type = std::pair<typename MapT::key_type, const void*>;
0225
0226
0227
0228
0229
0230
0231 struct const_iterator : public MapSorterIt<storage_type> {
0232 using pointer = const typename MapT::value_type*;
0233 using reference = const typename MapT::value_type&;
0234 using MapSorterIt<storage_type>::MapSorterIt;
0235
0236 pointer operator->() const {
0237 return static_cast<const value_type*>(this->ptr->second);
0238 }
0239 reference operator*() const { return *this->operator->(); }
0240 };
0241
0242 explicit MapSorterFlat(const MapT& m)
0243 : size_(m.size()), items_(size_ ? new storage_type[size_] : nullptr) {
0244 if (!size_) return;
0245 storage_type* it = &items_[0];
0246 for (const auto& entry : m) {
0247 *it++ = {entry.first, &entry};
0248 }
0249 std::sort(&items_[0], &items_[size_],
0250 MapSorterLessThan<typename MapT::key_type>{});
0251 }
0252 size_t size() const { return size_; }
0253 const_iterator begin() const { return {items_.get()}; }
0254 const_iterator end() const { return {items_.get() + size_}; }
0255
0256 private:
0257 size_t size_;
0258 std::unique_ptr<storage_type[]> items_;
0259 };
0260
0261
0262 template <typename KeyT>
0263 struct MapSorterPtrLessThan {
0264 bool operator()(const void* a, const void* b) const {
0265
0266
0267 return *reinterpret_cast<const KeyT*>(a) <
0268 *reinterpret_cast<const KeyT*>(b);
0269 }
0270 };
0271
0272
0273
0274 template <typename MapT>
0275 class MapSorterPtr {
0276 public:
0277 using value_type = typename MapT::value_type;
0278
0279
0280
0281 using storage_type = const void*;
0282
0283
0284
0285
0286
0287
0288 struct const_iterator : public MapSorterIt<storage_type> {
0289 using pointer = const typename MapT::value_type*;
0290 using reference = const typename MapT::value_type&;
0291 using MapSorterIt<storage_type>::MapSorterIt;
0292
0293 pointer operator->() const {
0294 return static_cast<const value_type*>(*this->ptr);
0295 }
0296 reference operator*() const { return *this->operator->(); }
0297 };
0298
0299 explicit MapSorterPtr(const MapT& m)
0300 : size_(m.size()), items_(size_ ? new storage_type[size_] : nullptr) {
0301 if (!size_) return;
0302 storage_type* it = &items_[0];
0303 for (const auto& entry : m) {
0304 *it++ = &entry;
0305 }
0306 static_assert(PROTOBUF_FIELD_OFFSET(typename MapT::value_type, first) == 0,
0307 "Must hold for MapSorterPtrLessThan to work.");
0308 std::sort(&items_[0], &items_[size_],
0309 MapSorterPtrLessThan<typename MapT::key_type>{});
0310 }
0311 size_t size() const { return size_; }
0312 const_iterator begin() const { return {items_.get()}; }
0313 const_iterator end() const { return {items_.get() + size_}; }
0314
0315 private:
0316 size_t size_;
0317 std::unique_ptr<storage_type[]> items_;
0318 };
0319
0320 struct WeakDescriptorDefaultTail {
0321 const Message** target;
0322 size_t size;
0323 };
0324
0325
0326
0327
0328
0329
0330
0331
0332 struct BytesTag {
0333 explicit BytesTag() = default;
0334 };
0335
0336
0337
0338
0339 inline void AssignToString(std::string& dest, const std::string& value,
0340 BytesTag tag = BytesTag{}) {
0341 dest.assign(value);
0342 }
0343 inline void AssignToString(std::string& dest, std::string&& value,
0344 BytesTag tag = BytesTag{}) {
0345 dest.assign(std::move(value));
0346 }
0347 inline void AssignToString(std::string& dest, const char* value,
0348 BytesTag tag = BytesTag{}) {
0349 dest.assign(value);
0350 }
0351 inline void AssignToString(std::string& dest, const char* value,
0352 std::size_t size) {
0353 dest.assign(value, size);
0354 }
0355 inline void AssignToString(std::string& dest, const void* value,
0356 std::size_t size, BytesTag tag) {
0357 dest.assign(reinterpret_cast<const char*>(value), size);
0358 }
0359 inline void AssignToString(std::string& dest, absl::string_view value,
0360 BytesTag tag = BytesTag{}) {
0361 dest.assign(value.data(), value.size());
0362 }
0363
0364
0365
0366
0367 template <typename Arg, typename... Args>
0368 void AddToRepeatedPtrField(google::protobuf::RepeatedPtrField<std::string>& dest,
0369 Arg&& value, Args... args) {
0370 AssignToString(*dest.Add(), std::forward<Arg>(value), args...);
0371 }
0372 inline void AddToRepeatedPtrField(google::protobuf::RepeatedPtrField<std::string>& dest,
0373 std::string&& value,
0374 BytesTag tag = BytesTag{}) {
0375 dest.Add(std::move(value));
0376 }
0377
0378 }
0379 }
0380 }
0381
0382 #include "google/protobuf/port_undef.inc"
0383
0384 #endif