We use TSA_NO_THREAD_SAFETY_ANALYSIS to prevent TSA complaining that we're modifying the query_status fields without locking the mutex. Since we're building it from scratch, there's no harm in not holding it. If we locked it to make TSA happy, TSAN build would falsely complain about `lock-order-inversion (potential deadlock)` which is not a real issue since QueryMetricLogStatus's mutex cannot be l
| 160 | /// which is not a real issue since QueryMetricLogStatus's mutex cannot be locked by anything else |
| 161 | /// until we add it to the queries map. |
| 162 | void QueryMetricLog::startQuery(const String & query_id, TimePoint start_time, UInt64 interval_milliseconds) TSA_NO_THREAD_SAFETY_ANALYSIS |
| 163 | { |
| 164 | QueryMetricLogStatus query_status; |
| 165 | QueryMetricLogStatusInfo & info = query_status.info; |
| 166 | info.interval_milliseconds = interval_milliseconds; |
| 167 | info.next_collect_time = start_time; |
| 168 | |
| 169 | auto context = getContext(); |
| 170 | const auto & process_list = context->getProcessList(); |
| 171 | info.task = context->getSchedulePool().createTask(StorageID::createEmpty(), "QueryMetricLog", [this, &process_list, query_id] { |
| 172 | collectMetric(process_list, query_id); |
| 173 | }); |
| 174 | |
| 175 | UniqueLock global_lock(queries_mutex); |
| 176 | query_status.scheduleNext(query_id); |
| 177 | queries.emplace(query_id, std::move(query_status)); |
| 178 | } |
| 179 | |
| 180 | void QueryMetricLog::finishQuery(const String & query_id, TimePoint finish_time, QueryStatusInfoPtr query_info) |
| 181 | { |
no test coverage detected