1 //===-- ProgressReportTest.cpp --------------------------------------------===// 2 // 3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4 // See https://llvm.org/LICENSE.txt for license information. 5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6 // 7 //===----------------------------------------------------------------------===// 8 9 #include "Plugins/Platform/MacOSX/PlatformMacOSX.h" 10 #include "Plugins/Platform/MacOSX/PlatformRemoteMacOSX.h" 11 #include "TestingSupport/SubsystemRAII.h" 12 #include "TestingSupport/TestUtilities.h" 13 #include "lldb/Core/Debugger.h" 14 #include "lldb/Core/Progress.h" 15 #include "lldb/Host/FileSystem.h" 16 #include "lldb/Host/HostInfo.h" 17 #include "lldb/Utility/Listener.h" 18 #include "gtest/gtest.h" 19 #include <memory> 20 #include <mutex> 21 #include <thread> 22 23 using namespace lldb; 24 using namespace lldb_private; 25 26 static std::chrono::milliseconds TIMEOUT(500); 27 28 class ProgressReportTest : public ::testing::Test { 29 public: 30 ListenerSP CreateListenerFor(uint32_t bit) { 31 // Set up the debugger, make sure that was done properly. 32 ArchSpec arch("x86_64-apple-macosx-"); 33 Platform::SetHostPlatform( 34 PlatformRemoteMacOSX::CreateInstance(true, &arch)); 35 36 m_debugger_sp = Debugger::CreateInstance(); 37 38 // Get the debugger's broadcaster. 39 Broadcaster &broadcaster = m_debugger_sp->GetBroadcaster(); 40 41 // Create a listener, make sure it can receive events and that it's 42 // listening to the correct broadcast bit. 43 m_listener_sp = Listener::MakeListener("progress-listener"); 44 m_listener_sp->StartListeningForEvents(&broadcaster, bit); 45 return m_listener_sp; 46 } 47 48 protected: 49 // The debugger's initialization function can't be called with no arguments 50 // so calling it using SubsystemRAII will cause the test build to fail as 51 // SubsystemRAII will call Initialize with no arguments. As such we set it up 52 // here the usual way. 53 void SetUp() override { 54 std::call_once(TestUtilities::g_debugger_initialize_flag, 55 []() { Debugger::Initialize(nullptr); }); 56 }; 57 58 DebuggerSP m_debugger_sp; 59 ListenerSP m_listener_sp; 60 SubsystemRAII<FileSystem, HostInfo, PlatformMacOSX, ProgressManager> 61 subsystems; 62 }; 63 64 TEST_F(ProgressReportTest, TestReportCreation) { 65 ListenerSP listener_sp = CreateListenerFor(lldb::eBroadcastBitProgress); 66 EventSP event_sp; 67 const ProgressEventData *data; 68 69 // Scope this for RAII on the progress objects. 70 // Create progress reports and check that their respective events for having 71 // started and ended are broadcasted. 72 { 73 Progress progress1("Progress report 1", "Starting report 1"); 74 Progress progress2("Progress report 2", "Starting report 2"); 75 Progress progress3("Progress report 3", "Starting report 3"); 76 } 77 78 // Start popping events from the queue, they should have been recevied 79 // in this order: 80 // Starting progress: 1, 2, 3 81 // Ending progress: 3, 2, 1 82 ASSERT_TRUE(listener_sp->GetEvent(event_sp, TIMEOUT)); 83 data = ProgressEventData::GetEventDataFromEvent(event_sp.get()); 84 85 EXPECT_EQ(data->GetDetails(), "Starting report 1"); 86 EXPECT_FALSE(data->IsFinite()); 87 EXPECT_FALSE(data->GetCompleted()); 88 EXPECT_EQ(data->GetTotal(), Progress::kNonDeterministicTotal); 89 EXPECT_EQ(data->GetMessage(), "Progress report 1: Starting report 1"); 90 91 ASSERT_TRUE(listener_sp->GetEvent(event_sp, TIMEOUT)); 92 data = ProgressEventData::GetEventDataFromEvent(event_sp.get()); 93 94 EXPECT_EQ(data->GetDetails(), "Starting report 2"); 95 EXPECT_FALSE(data->IsFinite()); 96 EXPECT_FALSE(data->GetCompleted()); 97 EXPECT_EQ(data->GetTotal(), Progress::kNonDeterministicTotal); 98 EXPECT_EQ(data->GetMessage(), "Progress report 2: Starting report 2"); 99 100 ASSERT_TRUE(listener_sp->GetEvent(event_sp, TIMEOUT)); 101 data = ProgressEventData::GetEventDataFromEvent(event_sp.get()); 102 103 EXPECT_EQ(data->GetDetails(), "Starting report 3"); 104 EXPECT_FALSE(data->IsFinite()); 105 EXPECT_FALSE(data->GetCompleted()); 106 EXPECT_EQ(data->GetTotal(), Progress::kNonDeterministicTotal); 107 EXPECT_EQ(data->GetMessage(), "Progress report 3: Starting report 3"); 108 109 // Progress report objects should be destroyed at this point so 110 // get each report from the queue and check that they've been 111 // destroyed in reverse order. 112 ASSERT_TRUE(listener_sp->GetEvent(event_sp, TIMEOUT)); 113 data = ProgressEventData::GetEventDataFromEvent(event_sp.get()); 114 115 EXPECT_EQ(data->GetTitle(), "Progress report 3"); 116 EXPECT_TRUE(data->GetCompleted()); 117 EXPECT_FALSE(data->IsFinite()); 118 EXPECT_EQ(data->GetMessage(), "Progress report 3: Starting report 3"); 119 120 ASSERT_TRUE(listener_sp->GetEvent(event_sp, TIMEOUT)); 121 data = ProgressEventData::GetEventDataFromEvent(event_sp.get()); 122 123 EXPECT_EQ(data->GetTitle(), "Progress report 2"); 124 EXPECT_TRUE(data->GetCompleted()); 125 EXPECT_FALSE(data->IsFinite()); 126 EXPECT_EQ(data->GetMessage(), "Progress report 2: Starting report 2"); 127 128 ASSERT_TRUE(listener_sp->GetEvent(event_sp, TIMEOUT)); 129 data = ProgressEventData::GetEventDataFromEvent(event_sp.get()); 130 131 EXPECT_EQ(data->GetTitle(), "Progress report 1"); 132 EXPECT_TRUE(data->GetCompleted()); 133 EXPECT_FALSE(data->IsFinite()); 134 EXPECT_EQ(data->GetMessage(), "Progress report 1: Starting report 1"); 135 } 136 137 TEST_F(ProgressReportTest, TestReportDestructionWithPartialProgress) { 138 ListenerSP listener_sp = CreateListenerFor(lldb::eBroadcastBitProgress); 139 EventSP event_sp; 140 const ProgressEventData *data; 141 142 // Create a finite progress report and only increment to a non-completed 143 // state before destruction. 144 { 145 Progress progress("Finite progress", "Report 1", 100); 146 progress.Increment(3); 147 } 148 149 // Verify that the progress in the events are: 150 // 1. At construction: 0 out of 100 151 // 2. At increment: 3 out of 100 152 // 3. At destruction: 100 out of 100 153 ASSERT_TRUE(listener_sp->GetEvent(event_sp, TIMEOUT)); 154 data = ProgressEventData::GetEventDataFromEvent(event_sp.get()); 155 EXPECT_EQ(data->GetDetails(), "Report 1"); 156 EXPECT_TRUE(data->IsFinite()); 157 EXPECT_EQ(data->GetCompleted(), (uint64_t)0); 158 EXPECT_EQ(data->GetTotal(), (uint64_t)100); 159 EXPECT_EQ(data->GetMessage(), "Finite progress: Report 1"); 160 161 ASSERT_TRUE(listener_sp->GetEvent(event_sp, TIMEOUT)); 162 data = ProgressEventData::GetEventDataFromEvent(event_sp.get()); 163 EXPECT_EQ(data->GetDetails(), "Report 1"); 164 EXPECT_TRUE(data->IsFinite()); 165 EXPECT_EQ(data->GetCompleted(), (uint64_t)3); 166 EXPECT_EQ(data->GetTotal(), (uint64_t)100); 167 EXPECT_EQ(data->GetMessage(), "Finite progress: Report 1"); 168 169 ASSERT_TRUE(listener_sp->GetEvent(event_sp, TIMEOUT)); 170 data = ProgressEventData::GetEventDataFromEvent(event_sp.get()); 171 EXPECT_EQ(data->GetDetails(), "Report 1"); 172 EXPECT_TRUE(data->IsFinite()); 173 EXPECT_EQ(data->GetCompleted(), (uint64_t)100); 174 EXPECT_EQ(data->GetTotal(), (uint64_t)100); 175 EXPECT_EQ(data->GetMessage(), "Finite progress: Report 1"); 176 177 // Create an infinite progress report and increment by some amount. 178 { 179 Progress progress("Infinite progress", "Report 2"); 180 progress.Increment(3); 181 } 182 183 // Verify that the progress in the events are: 184 // 1. At construction: 0 185 // 2. At increment: 3 186 // 3. At destruction: Progress::kNonDeterministicTotal 187 ASSERT_TRUE(listener_sp->GetEvent(event_sp, TIMEOUT)); 188 data = ProgressEventData::GetEventDataFromEvent(event_sp.get()); 189 EXPECT_EQ(data->GetDetails(), "Report 2"); 190 EXPECT_FALSE(data->IsFinite()); 191 EXPECT_EQ(data->GetCompleted(), (uint64_t)0); 192 EXPECT_EQ(data->GetTotal(), Progress::kNonDeterministicTotal); 193 EXPECT_EQ(data->GetMessage(), "Infinite progress: Report 2"); 194 195 ASSERT_TRUE(listener_sp->GetEvent(event_sp, TIMEOUT)); 196 data = ProgressEventData::GetEventDataFromEvent(event_sp.get()); 197 EXPECT_EQ(data->GetDetails(), "Report 2"); 198 EXPECT_FALSE(data->IsFinite()); 199 EXPECT_EQ(data->GetCompleted(), (uint64_t)3); 200 EXPECT_EQ(data->GetTotal(), Progress::kNonDeterministicTotal); 201 EXPECT_EQ(data->GetMessage(), "Infinite progress: Report 2"); 202 203 ASSERT_TRUE(listener_sp->GetEvent(event_sp, TIMEOUT)); 204 data = ProgressEventData::GetEventDataFromEvent(event_sp.get()); 205 EXPECT_EQ(data->GetDetails(), "Report 2"); 206 EXPECT_FALSE(data->IsFinite()); 207 EXPECT_EQ(data->GetCompleted(), Progress::kNonDeterministicTotal); 208 EXPECT_EQ(data->GetTotal(), Progress::kNonDeterministicTotal); 209 EXPECT_EQ(data->GetMessage(), "Infinite progress: Report 2"); 210 } 211 212 TEST_F(ProgressReportTest, TestFiniteOverflow) { 213 ListenerSP listener_sp = CreateListenerFor(lldb::eBroadcastBitProgress); 214 EventSP event_sp; 215 const ProgressEventData *data; 216 217 // Increment the report beyond its limit and make sure we only get one 218 // completed event. 219 { 220 Progress progress("Finite progress", "Report 1", 10); 221 progress.Increment(11); 222 progress.Increment(47); 223 } 224 225 ASSERT_TRUE(listener_sp->GetEvent(event_sp, TIMEOUT)); 226 data = ProgressEventData::GetEventDataFromEvent(event_sp.get()); 227 EXPECT_TRUE(data->IsFinite()); 228 EXPECT_EQ(data->GetCompleted(), 0U); 229 EXPECT_EQ(data->GetTotal(), 10U); 230 231 ASSERT_TRUE(listener_sp->GetEvent(event_sp, TIMEOUT)); 232 data = ProgressEventData::GetEventDataFromEvent(event_sp.get()); 233 EXPECT_TRUE(data->IsFinite()); 234 EXPECT_EQ(data->GetCompleted(), 10U); 235 EXPECT_EQ(data->GetTotal(), 10U); 236 237 ASSERT_FALSE(listener_sp->GetEvent(event_sp, TIMEOUT)); 238 } 239 240 TEST_F(ProgressReportTest, TestNonDeterministicOverflow) { 241 ListenerSP listener_sp = CreateListenerFor(lldb::eBroadcastBitProgress); 242 EventSP event_sp; 243 const ProgressEventData *data; 244 constexpr uint64_t max_minus_1 = std::numeric_limits<uint64_t>::max() - 1; 245 246 // Increment the report beyond its limit and make sure we only get one 247 // completed event. The event which overflows the counter should be ignored. 248 { 249 Progress progress("Non deterministic progress", "Report 1"); 250 progress.Increment(max_minus_1); 251 progress.Increment(max_minus_1); 252 } 253 254 ASSERT_TRUE(listener_sp->GetEvent(event_sp, TIMEOUT)); 255 data = ProgressEventData::GetEventDataFromEvent(event_sp.get()); 256 EXPECT_FALSE(data->IsFinite()); 257 EXPECT_EQ(data->GetCompleted(), 0U); 258 EXPECT_EQ(data->GetTotal(), Progress::kNonDeterministicTotal); 259 260 ASSERT_TRUE(listener_sp->GetEvent(event_sp, TIMEOUT)); 261 data = ProgressEventData::GetEventDataFromEvent(event_sp.get()); 262 EXPECT_FALSE(data->IsFinite()); 263 EXPECT_EQ(data->GetCompleted(), max_minus_1); 264 EXPECT_EQ(data->GetTotal(), Progress::kNonDeterministicTotal); 265 266 ASSERT_TRUE(listener_sp->GetEvent(event_sp, TIMEOUT)); 267 data = ProgressEventData::GetEventDataFromEvent(event_sp.get()); 268 EXPECT_FALSE(data->IsFinite()); 269 EXPECT_EQ(data->GetCompleted(), Progress::kNonDeterministicTotal); 270 EXPECT_EQ(data->GetTotal(), Progress::kNonDeterministicTotal); 271 272 ASSERT_FALSE(listener_sp->GetEvent(event_sp, TIMEOUT)); 273 } 274 275 TEST_F(ProgressReportTest, TestMinimumReportTime) { 276 ListenerSP listener_sp = CreateListenerFor(lldb::eBroadcastBitProgress); 277 EventSP event_sp; 278 const ProgressEventData *data; 279 280 { 281 Progress progress("Finite progress", "Report 1", /*total=*/20, 282 m_debugger_sp.get(), 283 /*minimum_report_time=*/std::chrono::seconds(1)); 284 // Send 10 events in quick succession. These should not generate any events. 285 for (int i = 0; i < 10; ++i) 286 progress.Increment(); 287 288 // Sleep, then send 10 more. This should generate one event for the first 289 // increment, and then another for completion. 290 std::this_thread::sleep_for(std::chrono::seconds(1)); 291 for (int i = 0; i < 10; ++i) 292 progress.Increment(); 293 } 294 295 ASSERT_TRUE(listener_sp->GetEvent(event_sp, TIMEOUT)); 296 data = ProgressEventData::GetEventDataFromEvent(event_sp.get()); 297 EXPECT_TRUE(data->IsFinite()); 298 EXPECT_EQ(data->GetCompleted(), 0U); 299 EXPECT_EQ(data->GetTotal(), 20U); 300 301 ASSERT_TRUE(listener_sp->GetEvent(event_sp, TIMEOUT)); 302 data = ProgressEventData::GetEventDataFromEvent(event_sp.get()); 303 EXPECT_TRUE(data->IsFinite()); 304 EXPECT_EQ(data->GetCompleted(), 11U); 305 EXPECT_EQ(data->GetTotal(), 20U); 306 307 ASSERT_TRUE(listener_sp->GetEvent(event_sp, TIMEOUT)); 308 data = ProgressEventData::GetEventDataFromEvent(event_sp.get()); 309 EXPECT_TRUE(data->IsFinite()); 310 EXPECT_EQ(data->GetCompleted(), 20U); 311 EXPECT_EQ(data->GetTotal(), 20U); 312 313 ASSERT_FALSE(listener_sp->GetEvent(event_sp, TIMEOUT)); 314 } 315 316 TEST_F(ProgressReportTest, TestProgressManager) { 317 ListenerSP listener_sp = 318 CreateListenerFor(lldb::eBroadcastBitProgressCategory); 319 EventSP event_sp; 320 const ProgressEventData *data; 321 322 // Create three progress events with the same category then try to pop 2 323 // events from the queue in a row before the progress reports are destroyed. 324 // Since only 1 event should've been broadcast for this category, the second 325 // GetEvent() call should return false. 326 { 327 Progress progress1("Progress report 1", "Starting report 1"); 328 Progress progress2("Progress report 1", "Starting report 2"); 329 Progress progress3("Progress report 1", "Starting report 3"); 330 ASSERT_TRUE(listener_sp->GetEvent(event_sp, TIMEOUT)); 331 ASSERT_FALSE(listener_sp->GetEvent(event_sp, TIMEOUT)); 332 } 333 334 data = ProgressEventData::GetEventDataFromEvent(event_sp.get()); 335 336 EXPECT_EQ(data->GetDetails(), ""); 337 EXPECT_FALSE(data->IsFinite()); 338 EXPECT_FALSE(data->GetCompleted()); 339 EXPECT_EQ(data->GetTotal(), Progress::kNonDeterministicTotal); 340 EXPECT_EQ(data->GetMessage(), "Progress report 1"); 341 342 // Pop another event from the queue, this should be the event for the final 343 // report for this category. 344 ASSERT_TRUE(listener_sp->GetEvent(event_sp, TIMEOUT)); 345 data = ProgressEventData::GetEventDataFromEvent(event_sp.get()); 346 347 EXPECT_EQ(data->GetDetails(), ""); 348 EXPECT_FALSE(data->IsFinite()); 349 EXPECT_TRUE(data->GetCompleted()); 350 EXPECT_EQ(data->GetTotal(), Progress::kNonDeterministicTotal); 351 EXPECT_EQ(data->GetMessage(), "Progress report 1"); 352 } 353 354 TEST_F(ProgressReportTest, TestOverlappingEvents) { 355 ListenerSP listener_sp = 356 CreateListenerFor(lldb::eBroadcastBitProgressCategory); 357 EventSP event_sp; 358 const ProgressEventData *data; 359 360 // Create two progress reports of the same category that overlap with each 361 // other. Here we want to ensure that the ID broadcasted for the initial and 362 // final reports for this category are the same. 363 std::unique_ptr<Progress> overlap_progress1 = 364 std::make_unique<Progress>("Overlapping report 1", "Starting report 1"); 365 std::unique_ptr<Progress> overlap_progress2 = 366 std::make_unique<Progress>("Overlapping report 1", "Starting report 2"); 367 overlap_progress1.reset(); 368 369 ASSERT_TRUE(listener_sp->GetEvent(event_sp, TIMEOUT)); 370 data = ProgressEventData::GetEventDataFromEvent(event_sp.get()); 371 // Get the ID used in the first report for this category. 372 uint64_t expected_progress_id = data->GetID(); 373 374 EXPECT_EQ(data->GetDetails(), ""); 375 EXPECT_FALSE(data->IsFinite()); 376 EXPECT_FALSE(data->GetCompleted()); 377 EXPECT_EQ(data->GetTotal(), Progress::kNonDeterministicTotal); 378 EXPECT_EQ(data->GetMessage(), "Overlapping report 1"); 379 380 overlap_progress2.reset(); 381 382 ASSERT_TRUE(listener_sp->GetEvent(event_sp, TIMEOUT)); 383 data = ProgressEventData::GetEventDataFromEvent(event_sp.get()); 384 385 EXPECT_EQ(data->GetDetails(), ""); 386 EXPECT_FALSE(data->IsFinite()); 387 EXPECT_TRUE(data->GetCompleted()); 388 EXPECT_EQ(data->GetTotal(), Progress::kNonDeterministicTotal); 389 EXPECT_EQ(data->GetMessage(), "Overlapping report 1"); 390 // The progress ID for the final report should be the same as that for the 391 // initial report. 392 EXPECT_EQ(data->GetID(), expected_progress_id); 393 } 394 395 TEST_F(ProgressReportTest, TestProgressManagerDisjointReports) { 396 ListenerSP listener_sp = 397 CreateListenerFor(lldb::eBroadcastBitProgressCategory); 398 EventSP event_sp; 399 const ProgressEventData *data; 400 uint64_t expected_progress_id; 401 402 { Progress progress("Coalesced report 1", "Starting report 1"); } 403 { Progress progress("Coalesced report 1", "Starting report 2"); } 404 { Progress progress("Coalesced report 1", "Starting report 3"); } 405 406 ASSERT_TRUE(listener_sp->GetEvent(event_sp, TIMEOUT)); 407 data = ProgressEventData::GetEventDataFromEvent(event_sp.get()); 408 expected_progress_id = data->GetID(); 409 410 EXPECT_EQ(data->GetDetails(), ""); 411 EXPECT_FALSE(data->IsFinite()); 412 EXPECT_FALSE(data->GetCompleted()); 413 EXPECT_EQ(data->GetTotal(), Progress::kNonDeterministicTotal); 414 EXPECT_EQ(data->GetMessage(), "Coalesced report 1"); 415 416 ASSERT_TRUE(listener_sp->GetEvent(event_sp, TIMEOUT)); 417 data = ProgressEventData::GetEventDataFromEvent(event_sp.get()); 418 419 EXPECT_EQ(data->GetID(), expected_progress_id); 420 EXPECT_EQ(data->GetDetails(), ""); 421 EXPECT_FALSE(data->IsFinite()); 422 EXPECT_TRUE(data->GetCompleted()); 423 EXPECT_EQ(data->GetTotal(), Progress::kNonDeterministicTotal); 424 EXPECT_EQ(data->GetMessage(), "Coalesced report 1"); 425 426 ASSERT_FALSE(listener_sp->GetEvent(event_sp, TIMEOUT)); 427 } 428 429 TEST_F(ProgressReportTest, TestExternalReportCreation) { 430 ListenerSP listener_sp = 431 CreateListenerFor(lldb::eBroadcastBitExternalProgress); 432 EventSP event_sp; 433 const ProgressEventData *data; 434 435 // Scope this for RAII on the progress objects. 436 // Create progress reports and check that their respective events for having 437 // started and ended are broadcasted. 438 { 439 Progress progress1("Progress report 1", "Starting report 1", 440 /*total=*/std::nullopt, /*debugger=*/nullptr, 441 /*minimum_report_time=*/std::chrono::seconds(0), 442 Progress::Origin::eExternal); 443 Progress progress2("Progress report 2", "Starting report 2", 444 /*total=*/std::nullopt, /*debugger=*/nullptr, 445 /*minimum_report_time=*/std::chrono::seconds(0), 446 Progress::Origin::eExternal); 447 Progress progress3("Progress report 3", "Starting report 3", 448 /*total=*/std::nullopt, /*debugger=*/nullptr, 449 /*minimum_report_time=*/std::chrono::seconds(0), 450 Progress::Origin::eExternal); 451 } 452 453 // Start popping events from the queue, they should have been recevied 454 // in this order: 455 // Starting progress: 1, 2, 3 456 // Ending progress: 3, 2, 1 457 ASSERT_TRUE(listener_sp->GetEvent(event_sp, TIMEOUT)); 458 data = ProgressEventData::GetEventDataFromEvent(event_sp.get()); 459 460 EXPECT_EQ(data->GetDetails(), "Starting report 1"); 461 EXPECT_FALSE(data->IsFinite()); 462 EXPECT_FALSE(data->GetCompleted()); 463 EXPECT_EQ(data->GetTotal(), Progress::kNonDeterministicTotal); 464 EXPECT_EQ(data->GetMessage(), "Progress report 1: Starting report 1"); 465 466 ASSERT_TRUE(listener_sp->GetEvent(event_sp, TIMEOUT)); 467 data = ProgressEventData::GetEventDataFromEvent(event_sp.get()); 468 469 EXPECT_EQ(data->GetDetails(), "Starting report 2"); 470 EXPECT_FALSE(data->IsFinite()); 471 EXPECT_FALSE(data->GetCompleted()); 472 EXPECT_EQ(data->GetTotal(), Progress::kNonDeterministicTotal); 473 EXPECT_EQ(data->GetMessage(), "Progress report 2: Starting report 2"); 474 475 ASSERT_TRUE(listener_sp->GetEvent(event_sp, TIMEOUT)); 476 data = ProgressEventData::GetEventDataFromEvent(event_sp.get()); 477 478 EXPECT_EQ(data->GetDetails(), "Starting report 3"); 479 EXPECT_FALSE(data->IsFinite()); 480 EXPECT_FALSE(data->GetCompleted()); 481 EXPECT_EQ(data->GetTotal(), Progress::kNonDeterministicTotal); 482 EXPECT_EQ(data->GetMessage(), "Progress report 3: Starting report 3"); 483 484 // Progress report objects should be destroyed at this point so 485 // get each report from the queue and check that they've been 486 // destroyed in reverse order. 487 ASSERT_TRUE(listener_sp->GetEvent(event_sp, TIMEOUT)); 488 data = ProgressEventData::GetEventDataFromEvent(event_sp.get()); 489 490 EXPECT_EQ(data->GetTitle(), "Progress report 3"); 491 EXPECT_TRUE(data->GetCompleted()); 492 EXPECT_FALSE(data->IsFinite()); 493 EXPECT_EQ(data->GetMessage(), "Progress report 3: Starting report 3"); 494 495 ASSERT_TRUE(listener_sp->GetEvent(event_sp, TIMEOUT)); 496 data = ProgressEventData::GetEventDataFromEvent(event_sp.get()); 497 498 EXPECT_EQ(data->GetTitle(), "Progress report 2"); 499 EXPECT_TRUE(data->GetCompleted()); 500 EXPECT_FALSE(data->IsFinite()); 501 EXPECT_EQ(data->GetMessage(), "Progress report 2: Starting report 2"); 502 503 ASSERT_TRUE(listener_sp->GetEvent(event_sp, TIMEOUT)); 504 data = ProgressEventData::GetEventDataFromEvent(event_sp.get()); 505 506 EXPECT_EQ(data->GetTitle(), "Progress report 1"); 507 EXPECT_TRUE(data->GetCompleted()); 508 EXPECT_FALSE(data->IsFinite()); 509 EXPECT_EQ(data->GetMessage(), "Progress report 1: Starting report 1"); 510 } 511 512 TEST_F(ProgressReportTest, TestExternalReportNotReceived) { 513 ListenerSP listener_sp = CreateListenerFor(lldb::eBroadcastBitProgress); 514 EventSP event_sp; 515 516 // Scope this for RAII on the progress objects. 517 // Create progress reports and check that their respective events for having 518 // started and ended are broadcasted. 519 { 520 Progress progress1("External Progress report 1", 521 "Starting external report 1", 522 /*total=*/std::nullopt, /*debugger=*/nullptr, 523 /*minimum_report_time=*/std::chrono::seconds(0), 524 Progress::Origin::eExternal); 525 } 526 527 ASSERT_FALSE(listener_sp->GetEvent(event_sp, TIMEOUT)); 528 } 529