1 //===-- LibiptDecoder.cpp --======-----------------------------------------===// 2 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 3 // See https://llvm.org/LICENSE.txt for license information. 4 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 5 // 6 //===----------------------------------------------------------------------===// 7 8 #include "LibiptDecoder.h" 9 #include "TraceIntelPT.h" 10 #include "lldb/Target/Process.h" 11 #include <optional> 12 13 using namespace lldb; 14 using namespace lldb_private; 15 using namespace lldb_private::trace_intel_pt; 16 using namespace llvm; 17 18 bool IsLibiptError(int status) { return status < 0; } 19 20 bool IsEndOfStream(int status) { 21 assert(status >= 0 && "We can't check if we reached the end of the stream if " 22 "we got a failed status"); 23 return status & pts_eos; 24 } 25 26 bool HasEvents(int status) { 27 assert(status >= 0 && "We can't check for events if we got a failed status"); 28 return status & pts_event_pending; 29 } 30 31 // RAII deleter for libipt's decoders 32 auto InsnDecoderDeleter = [](pt_insn_decoder *decoder) { 33 pt_insn_free_decoder(decoder); 34 }; 35 36 auto QueryDecoderDeleter = [](pt_query_decoder *decoder) { 37 pt_qry_free_decoder(decoder); 38 }; 39 40 using PtInsnDecoderUP = 41 std::unique_ptr<pt_insn_decoder, decltype(InsnDecoderDeleter)>; 42 43 using PtQueryDecoderUP = 44 std::unique_ptr<pt_query_decoder, decltype(QueryDecoderDeleter)>; 45 46 /// Create a basic configuration object limited to a given buffer that can be 47 /// used for many different decoders. 48 static Expected<pt_config> CreateBasicLibiptConfig(TraceIntelPT &trace_intel_pt, 49 ArrayRef<uint8_t> buffer) { 50 Expected<pt_cpu> cpu_info = trace_intel_pt.GetCPUInfo(); 51 if (!cpu_info) 52 return cpu_info.takeError(); 53 54 pt_config config; 55 pt_config_init(&config); 56 config.cpu = *cpu_info; 57 58 int status = pt_cpu_errata(&config.errata, &config.cpu); 59 if (IsLibiptError(status)) 60 return make_error<IntelPTError>(status); 61 62 // The libipt library does not modify the trace buffer, hence the 63 // following casts are safe. 64 config.begin = const_cast<uint8_t *>(buffer.data()); 65 config.end = const_cast<uint8_t *>(buffer.data() + buffer.size()); 66 return config; 67 } 68 69 /// Callback used by libipt for reading the process memory. 70 /// 71 /// More information can be found in 72 /// https://github.com/intel/libipt/blob/master/doc/man/pt_image_set_callback.3.md 73 static int ReadProcessMemory(uint8_t *buffer, size_t size, 74 const pt_asid * /* unused */, uint64_t pc, 75 void *context) { 76 Process *process = static_cast<Process *>(context); 77 78 Status error; 79 int bytes_read = process->ReadMemory(pc, buffer, size, error); 80 if (error.Fail()) 81 return -pte_nomap; 82 return bytes_read; 83 } 84 85 /// Set up the memory image callback for the given decoder. 86 static Error SetupMemoryImage(pt_insn_decoder *decoder, Process &process) { 87 pt_image *image = pt_insn_get_image(decoder); 88 89 int status = pt_image_set_callback(image, ReadProcessMemory, &process); 90 if (IsLibiptError(status)) 91 return make_error<IntelPTError>(status); 92 return Error::success(); 93 } 94 95 /// Create an instruction decoder for the given buffer and the given process. 96 static Expected<PtInsnDecoderUP> 97 CreateInstructionDecoder(TraceIntelPT &trace_intel_pt, ArrayRef<uint8_t> buffer, 98 Process &process) { 99 Expected<pt_config> config = CreateBasicLibiptConfig(trace_intel_pt, buffer); 100 if (!config) 101 return config.takeError(); 102 103 pt_insn_decoder *decoder_ptr = pt_insn_alloc_decoder(&*config); 104 if (!decoder_ptr) 105 return make_error<IntelPTError>(-pte_nomem); 106 107 PtInsnDecoderUP decoder_up(decoder_ptr, InsnDecoderDeleter); 108 109 if (Error err = SetupMemoryImage(decoder_ptr, process)) 110 return std::move(err); 111 112 return decoder_up; 113 } 114 115 /// Create a query decoder for the given buffer. The query decoder is the 116 /// highest level decoder that operates directly on packets and doesn't perform 117 /// actual instruction decoding. That's why it can be useful for inspecting a 118 /// raw trace without pinning it to a particular process. 119 static Expected<PtQueryDecoderUP> 120 CreateQueryDecoder(TraceIntelPT &trace_intel_pt, ArrayRef<uint8_t> buffer) { 121 Expected<pt_config> config = CreateBasicLibiptConfig(trace_intel_pt, buffer); 122 if (!config) 123 return config.takeError(); 124 125 pt_query_decoder *decoder_ptr = pt_qry_alloc_decoder(&*config); 126 if (!decoder_ptr) 127 return make_error<IntelPTError>(-pte_nomem); 128 129 return PtQueryDecoderUP(decoder_ptr, QueryDecoderDeleter); 130 } 131 132 /// Class used to identify anomalies in traces, which should often indicate a 133 /// fatal error in the trace. 134 class PSBBlockAnomalyDetector { 135 public: 136 PSBBlockAnomalyDetector(pt_insn_decoder &decoder, 137 TraceIntelPT &trace_intel_pt, 138 DecodedThread &decoded_thread) 139 : m_decoder(decoder), m_decoded_thread(decoded_thread) { 140 m_infinite_decoding_loop_threshold = 141 trace_intel_pt.GetGlobalProperties() 142 .GetInfiniteDecodingLoopVerificationThreshold(); 143 m_extremely_large_decoding_threshold = 144 trace_intel_pt.GetGlobalProperties() 145 .GetExtremelyLargeDecodingThreshold(); 146 m_next_infinite_decoding_loop_threshold = 147 m_infinite_decoding_loop_threshold; 148 } 149 150 /// \return 151 /// An \a llvm::Error if an anomaly that includes the last instruction item 152 /// in the trace, or \a llvm::Error::success otherwise. 153 Error DetectAnomaly() { 154 RefreshPacketOffset(); 155 uint64_t insn_added_since_last_packet_offset = 156 m_decoded_thread.GetTotalInstructionCount() - 157 m_insn_count_at_last_packet_offset; 158 159 // We want to check if we might have fallen in an infinite loop. As this 160 // check is not a no-op, we want to do it when we have a strong suggestion 161 // that things went wrong. First, we check how many instructions we have 162 // decoded since we processed an Intel PT packet for the last time. This 163 // number should be low, because at some point we should see branches, jumps 164 // or interrupts that require a new packet to be processed. Once we reach 165 // certain threshold we start analyzing the trace. 166 // 167 // We use the number of decoded instructions since the last Intel PT packet 168 // as a proxy because, in fact, we don't expect a single packet to give, 169 // say, 100k instructions. That would mean that there are 100k sequential 170 // instructions without any single branch, which is highly unlikely, or that 171 // we found an infinite loop using direct jumps, e.g. 172 // 173 // 0x0A: nop or pause 174 // 0x0C: jump to 0x0A 175 // 176 // which is indeed code that is found in the kernel. I presume we reach 177 // this kind of code in the decoder because we don't handle self-modified 178 // code in post-mortem kernel traces. 179 // 180 // We are right now only signaling the anomaly as a trace error, but it 181 // would be more conservative to also discard all the trace items found in 182 // this PSB. I prefer not to do that for the time being to give more 183 // exposure to this kind of anomalies and help debugging. Discarding the 184 // trace items would just make investigation harded. 185 // 186 // Finally, if the user wants to see if a specific thread has an anomaly, 187 // it's enough to run the `thread trace dump info` command and look for the 188 // count of this kind of errors. 189 190 if (insn_added_since_last_packet_offset >= 191 m_extremely_large_decoding_threshold) { 192 // In this case, we have decoded a massive amount of sequential 193 // instructions that don't loop. Honestly I wonder if this will ever 194 // happen, but better safe than sorry. 195 return createStringError( 196 inconvertibleErrorCode(), 197 "anomalous trace: possible infinite trace detected"); 198 } 199 if (insn_added_since_last_packet_offset == 200 m_next_infinite_decoding_loop_threshold) { 201 if (std::optional<uint64_t> loop_size = TryIdentifyInfiniteLoop()) { 202 return createStringError( 203 inconvertibleErrorCode(), 204 "anomalous trace: possible infinite loop detected of size %" PRIu64, 205 *loop_size); 206 } 207 m_next_infinite_decoding_loop_threshold *= 2; 208 } 209 return Error::success(); 210 } 211 212 private: 213 std::optional<uint64_t> TryIdentifyInfiniteLoop() { 214 // The infinite decoding loops we'll encounter are due to sequential 215 // instructions that repeat themselves due to direct jumps, therefore in a 216 // cycle each individual address will only appear once. We use this 217 // information to detect cycles by finding the last 2 ocurrences of the last 218 // instruction added to the trace. Then we traverse the trace making sure 219 // that these two instructions where the ends of a repeating loop. 220 221 // This is a utility that returns the most recent instruction index given a 222 // position in the trace. If the given position is an instruction, that 223 // position is returned. It skips non-instruction items. 224 auto most_recent_insn_index = 225 [&](uint64_t item_index) -> std::optional<uint64_t> { 226 while (true) { 227 if (m_decoded_thread.GetItemKindByIndex(item_index) == 228 lldb::eTraceItemKindInstruction) { 229 return item_index; 230 } 231 if (item_index == 0) 232 return std::nullopt; 233 item_index--; 234 } 235 return std::nullopt; 236 }; 237 // Similar to most_recent_insn_index but skips the starting position. 238 auto prev_insn_index = [&](uint64_t item_index) -> std::optional<uint64_t> { 239 if (item_index == 0) 240 return std::nullopt; 241 return most_recent_insn_index(item_index - 1); 242 }; 243 244 // We first find the most recent instruction. 245 std::optional<uint64_t> last_insn_index_opt = 246 *prev_insn_index(m_decoded_thread.GetItemsCount()); 247 if (!last_insn_index_opt) 248 return std::nullopt; 249 uint64_t last_insn_index = *last_insn_index_opt; 250 251 // We then find the most recent previous occurrence of that last 252 // instruction. 253 std::optional<uint64_t> last_insn_copy_index = 254 prev_insn_index(last_insn_index); 255 uint64_t loop_size = 1; 256 while (last_insn_copy_index && 257 m_decoded_thread.GetInstructionLoadAddress(*last_insn_copy_index) != 258 m_decoded_thread.GetInstructionLoadAddress(last_insn_index)) { 259 last_insn_copy_index = prev_insn_index(*last_insn_copy_index); 260 loop_size++; 261 } 262 if (!last_insn_copy_index) 263 return std::nullopt; 264 265 // Now we check if the segment between these last positions of the last 266 // instruction address is in fact a repeating loop. 267 uint64_t loop_elements_visited = 1; 268 uint64_t insn_index_a = last_insn_index, 269 insn_index_b = *last_insn_copy_index; 270 while (loop_elements_visited < loop_size) { 271 if (std::optional<uint64_t> prev = prev_insn_index(insn_index_a)) 272 insn_index_a = *prev; 273 else 274 return std::nullopt; 275 if (std::optional<uint64_t> prev = prev_insn_index(insn_index_b)) 276 insn_index_b = *prev; 277 else 278 return std::nullopt; 279 if (m_decoded_thread.GetInstructionLoadAddress(insn_index_a) != 280 m_decoded_thread.GetInstructionLoadAddress(insn_index_b)) 281 return std::nullopt; 282 loop_elements_visited++; 283 } 284 return loop_size; 285 } 286 287 // Refresh the internal counters if a new packet offset has been visited 288 void RefreshPacketOffset() { 289 lldb::addr_t new_packet_offset; 290 if (!IsLibiptError(pt_insn_get_offset(&m_decoder, &new_packet_offset)) && 291 new_packet_offset != m_last_packet_offset) { 292 m_last_packet_offset = new_packet_offset; 293 m_next_infinite_decoding_loop_threshold = 294 m_infinite_decoding_loop_threshold; 295 m_insn_count_at_last_packet_offset = 296 m_decoded_thread.GetTotalInstructionCount(); 297 } 298 } 299 300 pt_insn_decoder &m_decoder; 301 DecodedThread &m_decoded_thread; 302 lldb::addr_t m_last_packet_offset = LLDB_INVALID_ADDRESS; 303 uint64_t m_insn_count_at_last_packet_offset = 0; 304 uint64_t m_infinite_decoding_loop_threshold; 305 uint64_t m_next_infinite_decoding_loop_threshold; 306 uint64_t m_extremely_large_decoding_threshold; 307 }; 308 309 /// Class that decodes a raw buffer for a single PSB block using the low level 310 /// libipt library. It assumes that kernel and user mode instructions are not 311 /// mixed in the same PSB block. 312 /// 313 /// Throughout this code, the status of the decoder will be used to identify 314 /// events needed to be processed or errors in the decoder. The values can be 315 /// - negative: actual errors 316 /// - positive or zero: not an error, but a list of bits signaling the status 317 /// of the decoder, e.g. whether there are events that need to be decoded or 318 /// not. 319 class PSBBlockDecoder { 320 public: 321 /// \param[in] decoder 322 /// A decoder configured to start and end within the boundaries of the 323 /// given \p psb_block. 324 /// 325 /// \param[in] psb_block 326 /// The PSB block to decode. 327 /// 328 /// \param[in] next_block_ip 329 /// The starting ip at the next PSB block of the same thread if available. 330 /// 331 /// \param[in] decoded_thread 332 /// A \a DecodedThread object where the decoded instructions will be 333 /// appended to. It might have already some instructions. 334 /// 335 /// \param[in] tsc_upper_bound 336 /// Maximum allowed value of TSCs decoded from this PSB block. 337 /// Any of this PSB's data occurring after this TSC will be excluded. 338 PSBBlockDecoder(PtInsnDecoderUP &&decoder_up, const PSBBlock &psb_block, 339 std::optional<lldb::addr_t> next_block_ip, 340 DecodedThread &decoded_thread, TraceIntelPT &trace_intel_pt, 341 std::optional<DecodedThread::TSC> tsc_upper_bound) 342 : m_decoder_up(std::move(decoder_up)), m_psb_block(psb_block), 343 m_next_block_ip(next_block_ip), m_decoded_thread(decoded_thread), 344 m_anomaly_detector(*m_decoder_up, trace_intel_pt, decoded_thread), 345 m_tsc_upper_bound(tsc_upper_bound) {} 346 347 /// \param[in] trace_intel_pt 348 /// The main Trace object that own the PSB block. 349 /// 350 /// \param[in] decoder 351 /// A decoder configured to start and end within the boundaries of the 352 /// given \p psb_block. 353 /// 354 /// \param[in] psb_block 355 /// The PSB block to decode. 356 /// 357 /// \param[in] buffer 358 /// The raw intel pt trace for this block. 359 /// 360 /// \param[in] process 361 /// The process to decode. It provides the memory image to use for 362 /// decoding. 363 /// 364 /// \param[in] next_block_ip 365 /// The starting ip at the next PSB block of the same thread if available. 366 /// 367 /// \param[in] decoded_thread 368 /// A \a DecodedThread object where the decoded instructions will be 369 /// appended to. It might have already some instructions. 370 static Expected<PSBBlockDecoder> 371 Create(TraceIntelPT &trace_intel_pt, const PSBBlock &psb_block, 372 ArrayRef<uint8_t> buffer, Process &process, 373 std::optional<lldb::addr_t> next_block_ip, 374 DecodedThread &decoded_thread, 375 std::optional<DecodedThread::TSC> tsc_upper_bound) { 376 Expected<PtInsnDecoderUP> decoder_up = 377 CreateInstructionDecoder(trace_intel_pt, buffer, process); 378 if (!decoder_up) 379 return decoder_up.takeError(); 380 381 return PSBBlockDecoder(std::move(*decoder_up), psb_block, next_block_ip, 382 decoded_thread, trace_intel_pt, tsc_upper_bound); 383 } 384 385 void DecodePSBBlock() { 386 int status = pt_insn_sync_forward(m_decoder_up.get()); 387 assert(status >= 0 && 388 "Synchronization shouldn't fail because this PSB was previously " 389 "decoded correctly."); 390 391 // We emit a TSC before a sync event to more easily associate a timestamp to 392 // the sync event. If present, the current block's TSC would be the first 393 // TSC we'll see when processing events. 394 if (m_psb_block.tsc) 395 m_decoded_thread.NotifyTsc(*m_psb_block.tsc); 396 397 m_decoded_thread.NotifySyncPoint(m_psb_block.psb_offset); 398 399 DecodeInstructionsAndEvents(status); 400 } 401 402 private: 403 /// Append an instruction and return \b false if and only if a serious anomaly 404 /// has been detected. 405 bool AppendInstructionAndDetectAnomalies(const pt_insn &insn) { 406 m_decoded_thread.AppendInstruction(insn); 407 408 if (Error err = m_anomaly_detector.DetectAnomaly()) { 409 m_decoded_thread.AppendCustomError(toString(std::move(err)), 410 /*fatal=*/true); 411 return false; 412 } 413 return true; 414 } 415 /// Decode all the instructions and events of the given PSB block. The 416 /// decoding loop might stop abruptly if an infinite decoding loop is 417 /// detected. 418 void DecodeInstructionsAndEvents(int status) { 419 pt_insn insn; 420 421 while (true) { 422 status = ProcessPTEvents(status); 423 424 if (IsLibiptError(status)) 425 return; 426 else if (IsEndOfStream(status)) 427 break; 428 429 // The status returned by pt_insn_next will need to be processed 430 // by ProcessPTEvents in the next loop if it is not an error. 431 std::memset(&insn, 0, sizeof insn); 432 status = pt_insn_next(m_decoder_up.get(), &insn, sizeof(insn)); 433 434 if (IsLibiptError(status)) { 435 m_decoded_thread.AppendError(IntelPTError(status, insn.ip)); 436 return; 437 } else if (IsEndOfStream(status)) { 438 break; 439 } 440 441 if (!AppendInstructionAndDetectAnomalies(insn)) 442 return; 443 } 444 445 // We need to keep querying non-branching instructions until we hit the 446 // starting point of the next PSB. We won't see events at this point. This 447 // is based on 448 // https://github.com/intel/libipt/blob/master/doc/howto_libipt.md#parallel-decode 449 if (m_next_block_ip && insn.ip != 0) { 450 while (insn.ip != *m_next_block_ip) { 451 if (!AppendInstructionAndDetectAnomalies(insn)) 452 return; 453 454 status = pt_insn_next(m_decoder_up.get(), &insn, sizeof(insn)); 455 456 if (IsLibiptError(status)) { 457 m_decoded_thread.AppendError(IntelPTError(status, insn.ip)); 458 return; 459 } 460 } 461 } 462 } 463 464 /// Process the TSC of a decoded PT event. Specifically, check if this TSC 465 /// is below the TSC upper bound for this PSB. If the TSC exceeds the upper 466 /// bound, return an error to abort decoding. Otherwise add the it to the 467 /// underlying DecodedThread and decoding should continue as expected. 468 /// 469 /// \param[in] tsc 470 /// The TSC of the a decoded event. 471 Error ProcessPTEventTSC(DecodedThread::TSC tsc) { 472 if (m_tsc_upper_bound && tsc >= *m_tsc_upper_bound) { 473 // This event and all the remaining events of this PSB have a TSC 474 // outside the range of the "owning" ThreadContinuousExecution. For 475 // now we drop all of these events/instructions, future work can 476 // improve upon this by determining the "owning" 477 // ThreadContinuousExecution of the remaining PSB data. 478 std::string err_msg = formatv("decoding truncated: TSC {0} exceeds " 479 "maximum TSC value {1}, will skip decoding" 480 " the remaining data of the PSB", 481 tsc, *m_tsc_upper_bound) 482 .str(); 483 484 uint64_t offset; 485 int status = pt_insn_get_offset(m_decoder_up.get(), &offset); 486 if (!IsLibiptError(status)) { 487 err_msg = formatv("{2} (skipping {0} of {1} bytes)", offset, 488 m_psb_block.size, err_msg) 489 .str(); 490 } 491 m_decoded_thread.AppendCustomError(err_msg); 492 return createStringError(inconvertibleErrorCode(), err_msg); 493 } else { 494 m_decoded_thread.NotifyTsc(tsc); 495 return Error::success(); 496 } 497 } 498 499 /// Before querying instructions, we need to query the events associated with 500 /// that instruction, e.g. timing and trace disablement events. 501 /// 502 /// \param[in] status 503 /// The status gotten from the previous instruction decoding or PSB 504 /// synchronization. 505 /// 506 /// \return 507 /// The pte_status after decoding events. 508 int ProcessPTEvents(int status) { 509 while (HasEvents(status)) { 510 pt_event event; 511 std::memset(&event, 0, sizeof event); 512 status = pt_insn_event(m_decoder_up.get(), &event, sizeof(event)); 513 514 if (IsLibiptError(status)) { 515 m_decoded_thread.AppendError(IntelPTError(status)); 516 return status; 517 } 518 519 if (event.has_tsc) { 520 if (Error err = ProcessPTEventTSC(event.tsc)) { 521 consumeError(std::move(err)); 522 return -pte_internal; 523 } 524 } 525 526 switch (event.type) { 527 case ptev_disabled: 528 // The CPU paused tracing the program, e.g. due to ip filtering. 529 m_decoded_thread.AppendEvent(lldb::eTraceEventDisabledHW); 530 break; 531 case ptev_async_disabled: 532 // The kernel or user code paused tracing the program, e.g. 533 // a breakpoint or a ioctl invocation pausing the trace, or a 534 // context switch happened. 535 m_decoded_thread.AppendEvent(lldb::eTraceEventDisabledSW); 536 break; 537 case ptev_overflow: 538 // The CPU internal buffer had an overflow error and some instructions 539 // were lost. A OVF packet comes with an FUP packet (harcoded address) 540 // according to the documentation, so we'll continue seeing instructions 541 // after this event. 542 m_decoded_thread.AppendError(IntelPTError(-pte_overflow)); 543 break; 544 default: 545 break; 546 } 547 } 548 549 return status; 550 } 551 552 private: 553 PtInsnDecoderUP m_decoder_up; 554 PSBBlock m_psb_block; 555 std::optional<lldb::addr_t> m_next_block_ip; 556 DecodedThread &m_decoded_thread; 557 PSBBlockAnomalyDetector m_anomaly_detector; 558 std::optional<DecodedThread::TSC> m_tsc_upper_bound; 559 }; 560 561 Error lldb_private::trace_intel_pt::DecodeSingleTraceForThread( 562 DecodedThread &decoded_thread, TraceIntelPT &trace_intel_pt, 563 ArrayRef<uint8_t> buffer) { 564 Expected<std::vector<PSBBlock>> blocks = 565 SplitTraceIntoPSBBlock(trace_intel_pt, buffer, /*expect_tscs=*/false); 566 if (!blocks) 567 return blocks.takeError(); 568 569 for (size_t i = 0; i < blocks->size(); i++) { 570 PSBBlock &block = blocks->at(i); 571 572 Expected<PSBBlockDecoder> decoder = PSBBlockDecoder::Create( 573 trace_intel_pt, block, buffer.slice(block.psb_offset, block.size), 574 *decoded_thread.GetThread()->GetProcess(), 575 i + 1 < blocks->size() ? blocks->at(i + 1).starting_ip : std::nullopt, 576 decoded_thread, std::nullopt); 577 if (!decoder) 578 return decoder.takeError(); 579 580 decoder->DecodePSBBlock(); 581 } 582 583 return Error::success(); 584 } 585 586 Error lldb_private::trace_intel_pt::DecodeSystemWideTraceForThread( 587 DecodedThread &decoded_thread, TraceIntelPT &trace_intel_pt, 588 const DenseMap<lldb::cpu_id_t, llvm::ArrayRef<uint8_t>> &buffers, 589 const std::vector<IntelPTThreadContinousExecution> &executions) { 590 bool has_seen_psbs = false; 591 for (size_t i = 0; i < executions.size(); i++) { 592 const IntelPTThreadContinousExecution &execution = executions[i]; 593 594 auto variant = execution.thread_execution.variant; 595 596 // We emit the first valid tsc 597 if (execution.psb_blocks.empty()) { 598 decoded_thread.NotifyTsc(execution.thread_execution.GetLowestKnownTSC()); 599 } else { 600 assert(execution.psb_blocks.front().tsc && 601 "per cpu decoding expects TSCs"); 602 decoded_thread.NotifyTsc( 603 std::min(execution.thread_execution.GetLowestKnownTSC(), 604 *execution.psb_blocks.front().tsc)); 605 } 606 607 // We then emit the CPU, which will be correctly associated with a tsc. 608 decoded_thread.NotifyCPU(execution.thread_execution.cpu_id); 609 610 // If we haven't seen a PSB yet, then it's fine not to show errors 611 if (has_seen_psbs) { 612 if (execution.psb_blocks.empty()) { 613 decoded_thread.AppendCustomError( 614 formatv("Unable to find intel pt data a thread " 615 "execution on cpu id = {0}", 616 execution.thread_execution.cpu_id) 617 .str()); 618 } 619 620 // A hinted start is a non-initial execution that doesn't have a switch 621 // in. An only end is an initial execution that doesn't have a switch in. 622 // Any of those cases represent a gap because we have seen a PSB before. 623 if (variant == ThreadContinuousExecution::Variant::HintedStart || 624 variant == ThreadContinuousExecution::Variant::OnlyEnd) { 625 decoded_thread.AppendCustomError( 626 formatv("Unable to find the context switch in for a thread " 627 "execution on cpu id = {0}", 628 execution.thread_execution.cpu_id) 629 .str()); 630 } 631 } 632 633 for (size_t j = 0; j < execution.psb_blocks.size(); j++) { 634 const PSBBlock &psb_block = execution.psb_blocks[j]; 635 636 Expected<PSBBlockDecoder> decoder = PSBBlockDecoder::Create( 637 trace_intel_pt, psb_block, 638 buffers.lookup(execution.thread_execution.cpu_id) 639 .slice(psb_block.psb_offset, psb_block.size), 640 *decoded_thread.GetThread()->GetProcess(), 641 j + 1 < execution.psb_blocks.size() 642 ? execution.psb_blocks[j + 1].starting_ip 643 : std::nullopt, 644 decoded_thread, execution.thread_execution.GetEndTSC()); 645 if (!decoder) 646 return decoder.takeError(); 647 648 has_seen_psbs = true; 649 decoder->DecodePSBBlock(); 650 } 651 652 // If we haven't seen a PSB yet, then it's fine not to show errors 653 if (has_seen_psbs) { 654 // A hinted end is a non-ending execution that doesn't have a switch out. 655 // An only start is an ending execution that doesn't have a switch out. 656 // Any of those cases represent a gap if we still have executions to 657 // process and we have seen a PSB before. 658 if (i + 1 != executions.size() && 659 (variant == ThreadContinuousExecution::Variant::OnlyStart || 660 variant == ThreadContinuousExecution::Variant::HintedEnd)) { 661 decoded_thread.AppendCustomError( 662 formatv("Unable to find the context switch out for a thread " 663 "execution on cpu id = {0}", 664 execution.thread_execution.cpu_id) 665 .str()); 666 } 667 } 668 } 669 return Error::success(); 670 } 671 672 bool IntelPTThreadContinousExecution::operator<( 673 const IntelPTThreadContinousExecution &o) const { 674 // As the context switch might be incomplete, we look first for the first real 675 // PSB packet, which is a valid TSC. Otherwise, We query the thread execution 676 // itself for some tsc. 677 auto get_tsc = [](const IntelPTThreadContinousExecution &exec) { 678 return exec.psb_blocks.empty() ? exec.thread_execution.GetLowestKnownTSC() 679 : exec.psb_blocks.front().tsc; 680 }; 681 682 return get_tsc(*this) < get_tsc(o); 683 } 684 685 Expected<std::vector<PSBBlock>> 686 lldb_private::trace_intel_pt::SplitTraceIntoPSBBlock( 687 TraceIntelPT &trace_intel_pt, llvm::ArrayRef<uint8_t> buffer, 688 bool expect_tscs) { 689 // This follows 690 // https://github.com/intel/libipt/blob/master/doc/howto_libipt.md#parallel-decode 691 692 Expected<PtQueryDecoderUP> decoder_up = 693 CreateQueryDecoder(trace_intel_pt, buffer); 694 if (!decoder_up) 695 return decoder_up.takeError(); 696 697 pt_query_decoder *decoder = decoder_up.get().get(); 698 699 std::vector<PSBBlock> executions; 700 701 while (true) { 702 uint64_t maybe_ip = LLDB_INVALID_ADDRESS; 703 int decoding_status = pt_qry_sync_forward(decoder, &maybe_ip); 704 if (IsLibiptError(decoding_status)) 705 break; 706 707 uint64_t psb_offset; 708 int offset_status = pt_qry_get_sync_offset(decoder, &psb_offset); 709 assert(offset_status >= 0 && 710 "This can't fail because we were able to synchronize"); 711 712 std::optional<uint64_t> ip; 713 if (!(pts_ip_suppressed & decoding_status)) 714 ip = maybe_ip; 715 716 std::optional<uint64_t> tsc; 717 // Now we fetch the first TSC that comes after the PSB. 718 while (HasEvents(decoding_status)) { 719 pt_event event; 720 decoding_status = pt_qry_event(decoder, &event, sizeof(event)); 721 if (IsLibiptError(decoding_status)) 722 break; 723 if (event.has_tsc) { 724 tsc = event.tsc; 725 break; 726 } 727 } 728 if (IsLibiptError(decoding_status)) { 729 // We continue to the next PSB. This effectively merges this PSB with the 730 // previous one, and that should be fine because this PSB might be the 731 // direct continuation of the previous thread and it's better to show an 732 // error in the decoded thread than to hide it. If this is the first PSB, 733 // we are okay losing it. Besides that, an error at processing events 734 // means that we wouldn't be able to get any instruction out of it. 735 continue; 736 } 737 738 if (expect_tscs && !tsc) 739 return createStringError(inconvertibleErrorCode(), 740 "Found a PSB without TSC."); 741 742 executions.push_back({ 743 psb_offset, 744 tsc, 745 0, 746 ip, 747 }); 748 } 749 if (!executions.empty()) { 750 // We now adjust the sizes of each block 751 executions.back().size = buffer.size() - executions.back().psb_offset; 752 for (int i = (int)executions.size() - 2; i >= 0; i--) { 753 executions[i].size = 754 executions[i + 1].psb_offset - executions[i].psb_offset; 755 } 756 } 757 return executions; 758 } 759 760 Expected<std::optional<uint64_t>> 761 lldb_private::trace_intel_pt::FindLowestTSCInTrace(TraceIntelPT &trace_intel_pt, 762 ArrayRef<uint8_t> buffer) { 763 Expected<PtQueryDecoderUP> decoder_up = 764 CreateQueryDecoder(trace_intel_pt, buffer); 765 if (!decoder_up) 766 return decoder_up.takeError(); 767 768 pt_query_decoder *decoder = decoder_up.get().get(); 769 uint64_t ip = LLDB_INVALID_ADDRESS; 770 int status = pt_qry_sync_forward(decoder, &ip); 771 if (IsLibiptError(status)) 772 return std::nullopt; 773 774 while (HasEvents(status)) { 775 pt_event event; 776 status = pt_qry_event(decoder, &event, sizeof(event)); 777 if (IsLibiptError(status)) 778 return std::nullopt; 779 if (event.has_tsc) 780 return event.tsc; 781 } 782 return std::nullopt; 783 } 784