1 /* 2 * Copyright (c) 2021-2022 Huawei Device Co., Ltd. 3 * Licensed under the Apache License, Version 2.0 (the "License"); 4 * you may not use this file except in compliance with the License. 5 * You may obtain a copy of the License at 6 * 7 * http://www.apache.org/licenses/LICENSE-2.0 8 * 9 * Unless required by applicable law or agreed to in writing, software 10 * distributed under the License is distributed on an "AS IS" BASIS, 11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 * See the License for the specific language governing permissions and 13 * limitations under the License. 14 */ 15 16 #ifndef HIVIEW_BASE_SYS_EVENT_H 17 #define HIVIEW_BASE_SYS_EVENT_H 18 19 #include <atomic> 20 #include <iomanip> 21 #include <memory> 22 #include <sstream> 23 #include <string> 24 #include <type_traits> 25 #include <vector> 26 27 #include "pipeline.h" 28 29 namespace OHOS { 30 namespace HiviewDFX { 31 class SysEventCreator; 32 enum ParseStatus { 33 STATE_PARSING_DOMAIN, 34 STATE_PARSING_NAME, 35 STATE_PARSING_TYPE, 36 STATE_PARSING_TIME, 37 STATE_PARSING_EVENT_SEQ, 38 STATE_PARSING_TZONE, 39 STATE_PARSING_PID, 40 STATE_PARSING_TID, 41 STATE_PARSING_UID, 42 STATE_PARSING_TRACE_ID, 43 STATE_PARSING_SPAN_ID, 44 STATE_PARSING_PARENT_SPAN_ID, 45 STATE_PARSING_TRACE_FLAG, 46 }; 47 struct ParseItem { 48 const char* keyString; 49 const char* valueStart; 50 const char* valueEnd1; 51 const char* valueEnd2; 52 ParseStatus status; 53 bool isParseContinue; 54 }; 55 56 class SysEvent : public PipelineEvent { 57 public: 58 SysEvent(const std::string& sender, PipelineEventProducer* handler, const std::string& jsonStr); 59 SysEvent(const std::string& sender, PipelineEventProducer* handler, SysEventCreator& sysEventCreator); 60 ~SysEvent(); 61 public: 62 int ParseJson(); 63 int32_t GetPid() const; 64 int32_t GetTid() const; 65 int32_t GetUid() const; 66 int16_t GetTz() const; 67 void SetSeq(int64_t); 68 int64_t GetSeq() const; 69 int64_t GetEventSeq() const; 70 std::string GetEventValue(const std::string& key); 71 uint64_t GetEventIntValue(const std::string& key); 72 void SetEventValue(const std::string& key, int64_t value); 73 void SetEventValue(const std::string& key, const std::string& value, bool append = false); 74 75 public: 76 static std::atomic<uint32_t> totalCount_; 77 static std::atomic<int64_t> totalSize_; 78 79 private: 80 int64_t seq_; 81 int32_t pid_; 82 int32_t tid_; 83 int32_t uid_; 84 int16_t tz_; 85 int64_t eventSeq_ = 0; 86 void InitialMember(ParseStatus status, const std::string &content); 87 }; 88 89 class SysEventCreator { 90 public: 91 enum EventType { 92 FAULT = 1, // system fault event 93 STATISTIC = 2, // system statistic event 94 SECURITY = 3, // system security event 95 BEHAVIOR = 4 // system behavior event 96 }; 97 public: 98 SysEventCreator(const std::string &domain, const std::string &eventName, EventType type); 99 100 template <typename T, typename U, typename... Rest> 101 struct is_one_of : std::conditional_t<std::is_same_v<typename std::decay_t<T>, typename std::decay_t<U>>, 102 std::true_type, is_one_of<T, Rest...>> {}; 103 104 template <typename T, typename U> 105 struct is_one_of<T, U> : std::conditional_t<std::is_same_v<typename std::decay_t<T>, typename std::decay_t<U>>, 106 std::true_type, std::false_type> {}; 107 108 template <typename Inst, template <typename...> typename Tmpl> 109 struct is_instantiation_of : std::false_type {}; 110 111 template <template <typename...> typename Tmpl, typename... Args> 112 struct is_instantiation_of<Tmpl<Args...>, Tmpl> : std::true_type {}; 113 114 // supported types of the key 115 template <typename T> 116 struct is_type_key : is_one_of<T, char *, char const *, std::string>::type {}; 117 118 template <typename T> 119 inline static constexpr bool is_type_key_v = is_type_key<T>::value; 120 121 // supported base types of the value 122 template <typename T> 123 struct is_type_value_base : is_one_of<T, bool, char, signed char, unsigned char, short, unsigned short, int, 124 unsigned int, long, unsigned long, long long, unsigned long long, float, double, char *, char const *, 125 std::string>::type {}; 126 127 template <typename T> 128 inline static constexpr bool is_type_value_base_v = is_type_value_base<T>::value; 129 130 // supported vector types of the value 131 template <typename T> 132 inline static constexpr bool is_type_value_vector_v = []() { 133 if constexpr(is_instantiation_of<typename std::decay_t<T>, std::vector>::value) { 134 return is_type_value_base_v<typename std::decay_t<T>::value_type>; 135 } 136 return false; 137 }(); 138 139 template<typename T> 140 static decltype(auto) GetItem(T&& item) 141 { 142 if constexpr(is_one_of<T, char, signed char, unsigned char>::value) { 143 return static_cast<short>(item); 144 } else if constexpr(is_one_of<T, char *, char const *, std::string>::value) { 145 std::string result; 146 result.append("\"").append(EscapeStringValue(item)).append("\""); 147 return result; 148 } else { 149 return std::forward<T>(item); 150 } 151 } 152 153 template<typename K, typename V> 154 SysEventCreator& SetKeyValue(K&& key, V&& value) 155 { 156 jsonStr_ << GetItem(std::forward<K>(key)) << ":"; 157 if constexpr(is_type_value_base_v<V>) { 158 jsonStr_ << GetItem(std::forward<V>(value)) << ","; 159 } else if constexpr(is_type_value_vector_v<V>) { 160 jsonStr_ << "["; 161 for (const auto &it : value) { 162 jsonStr_ << GetItem(it) << ","; 163 } 164 if (!value.empty()) { 165 jsonStr_.seekp(-1, std::ios_base::end); 166 } 167 jsonStr_ << "],"; 168 } 169 return *this; 170 } 171 172 private: 173 friend class SysEvent; 174 std::string BuildSysEventJson(); 175 static std::string EscapeStringValue(const std::string &value); 176 static std::string EscapeStringValue(const char* value); 177 static std::string EscapeStringValue(char* value); 178 private: 179 std::stringstream jsonStr_; 180 }; 181 } // namespace HiviewDFX 182 } // namespace OHOS 183 #endif // HIVIEW_BASE_SYS_EVENT_H 184