|
15 | 15 | #include "llvm/Config/llvm-config.h" |
16 | 16 | #include "llvm/Support/Debug.h" |
17 | 17 | #include "llvm/Support/Parallel.h" |
18 | | -#include "llvm/Support/Program.h" |
19 | 18 | #include "llvm/Support/ThreadPool.h" |
20 | 19 | #include "llvm/Support/raw_ostream.h" |
21 | 20 | #include "gtest/gtest.h" |
|
41 | 40 |
|
42 | 41 | using namespace llvm; |
43 | 42 |
|
44 | | -// Provided by the unit test main to locate the current test binary. |
45 | | -extern const char *TestMainArgv0; |
46 | | - |
47 | 43 | namespace { |
48 | 44 |
|
49 | | -// Unique anchor whose address helps locate the current test binary. |
50 | | -static int JobserverTestAnchor = 0; |
51 | | - |
52 | 45 | // RAII helper to set an environment variable for the duration of a test. |
53 | 46 | class ScopedEnvironment { |
54 | 47 | std::string Name; |
@@ -389,93 +382,51 @@ TEST_F(JobserverStrategyTest, ThreadPoolConcurrencyIsLimited) { |
389 | 382 | EXPECT_EQ(CompletedTasks, NumTasks); |
390 | 383 | } |
391 | 384 |
|
392 | | -// Parent-side driver that spawns a fresh process to run the child test which |
393 | | -// validates that parallelFor respects the jobserver limit when it is the first |
394 | | -// user of the default executor in that process. |
395 | | -TEST_F(JobserverStrategyTest, ParallelForIsLimited_Subprocess) { |
396 | | - // Mark child execution. |
397 | | - setenv("LLVM_JOBSERVER_TEST_CHILD", "1", 1); |
398 | | - |
399 | | - // Find the current test binary and build args to run only the child test. |
400 | | - std::string Executable = |
401 | | - sys::fs::getMainExecutable(TestMainArgv0, &JobserverTestAnchor); |
402 | | - ASSERT_FALSE(Executable.empty()) << "Failed to get main executable path"; |
403 | | - SmallVector<StringRef, 4> Args{Executable, |
404 | | - "--gtest_filter=JobserverStrategyTest." |
405 | | - "ParallelForIsLimited_SubprocessChild"}; |
406 | | - |
407 | | - std::string Error; |
408 | | - bool ExecFailed = false; |
409 | | - int RC = sys::ExecuteAndWait(Executable, Args, std::nullopt, {}, 0, 0, &Error, |
410 | | - &ExecFailed); |
411 | | - unsetenv("LLVM_JOBSERVER_TEST_CHILD"); |
412 | | - ASSERT_FALSE(ExecFailed) << Error; |
413 | | - ASSERT_EQ(RC, 0) << "Executable failed with exit code " << RC; |
414 | | -} |
415 | | - |
416 | | -// Child-side test: create FIFO and make-proxy in this process, set the |
417 | | -// jobserver strategy, and then run parallelFor. |
418 | | -TEST_F(JobserverStrategyTest, ParallelForIsLimited_SubprocessChild) { |
419 | | - if (!getenv("LLVM_JOBSERVER_TEST_CHILD")) |
420 | | - GTEST_SKIP() << "Not running in child mode"; |
421 | | - |
| 385 | +TEST_F(JobserverStrategyTest, ParallelForIsLimited) { |
422 | 386 | // This test verifies that llvm::parallelFor respects the jobserver limit. |
423 | 387 | const int NumExplicitJobs = 3; |
424 | 388 | const int ConcurrencyLimit = NumExplicitJobs + 1; // +1 implicit |
425 | 389 | const int NumTasks = 20; |
426 | 390 |
|
| 391 | + LLVM_DEBUG(dbgs() << "Calling startMakeProxy with " << NumExplicitJobs |
| 392 | + << " jobs.\n"); |
427 | 393 | startMakeProxy(NumExplicitJobs); |
| 394 | + LLVM_DEBUG(dbgs() << "MakeProxy is running.\n"); |
428 | 395 |
|
429 | | - // Set the global strategy before any default executor is created. |
| 396 | + // Set the global strategy. parallelFor will use this. |
430 | 397 | parallel::strategy = jobserver_concurrency(); |
431 | 398 |
|
432 | 399 | std::atomic<int> ActiveTasks{0}; |
433 | 400 | std::atomic<int> MaxActiveTasks{0}; |
434 | 401 |
|
435 | | - parallelFor(0, NumTasks, [&]([[maybe_unused]] int i) { |
| 402 | + parallelFor(0, NumTasks, [&](int i) { |
436 | 403 | int CurrentActive = ++ActiveTasks; |
| 404 | + LLVM_DEBUG(dbgs() << "Task " << i << ": Active tasks: " << CurrentActive |
| 405 | + << "\n"); |
437 | 406 | int OldMax = MaxActiveTasks.load(); |
438 | 407 | while (CurrentActive > OldMax) |
439 | 408 | MaxActiveTasks.compare_exchange_weak(OldMax, CurrentActive); |
| 409 | + |
440 | 410 | std::this_thread::sleep_for(std::chrono::milliseconds(20)); |
441 | 411 | --ActiveTasks; |
442 | 412 | }); |
443 | 413 |
|
| 414 | + LLVM_DEBUG(dbgs() << "ParallelFor finished. Max active tasks was " |
| 415 | + << MaxActiveTasks << ".\n"); |
444 | 416 | EXPECT_LE(MaxActiveTasks, ConcurrencyLimit); |
445 | 417 | } |
446 | 418 |
|
447 | | -// Parent-side driver for parallelSort child test. |
448 | | -TEST_F(JobserverStrategyTest, ParallelSortIsLimited_Subprocess) { |
449 | | - setenv("LLVM_JOBSERVER_TEST_CHILD", "1", 1); |
450 | | - |
451 | | - std::string Executable = |
452 | | - sys::fs::getMainExecutable(TestMainArgv0, &JobserverTestAnchor); |
453 | | - ASSERT_FALSE(Executable.empty()) << "Failed to get main executable path"; |
454 | | - SmallVector<StringRef, 4> Args{Executable, |
455 | | - "--gtest_filter=JobserverStrategyTest." |
456 | | - "ParallelSortIsLimited_SubprocessChild"}; |
457 | | - |
458 | | - std::string Error; |
459 | | - bool ExecFailed = false; |
460 | | - int RC = sys::ExecuteAndWait(Executable, Args, std::nullopt, {}, 0, 0, &Error, |
461 | | - &ExecFailed); |
462 | | - unsetenv("LLVM_JOBSERVER_TEST_CHILD"); |
463 | | - ASSERT_FALSE(ExecFailed) << Error; |
464 | | - ASSERT_EQ(RC, 0) << "Executable failed with exit code " << RC; |
465 | | -} |
466 | | - |
467 | | -// Child-side test: ensure parallelSort runs and completes correctly under the |
468 | | -// jobserver strategy when it owns default executor initialization. |
469 | | -TEST_F(JobserverStrategyTest, ParallelSortIsLimited_SubprocessChild) { |
470 | | - if (!getenv("LLVM_JOBSERVER_TEST_CHILD")) |
471 | | - GTEST_SKIP() << "Not running in child mode"; |
472 | | - |
| 419 | +TEST_F(JobserverStrategyTest, ParallelSortIsLimited) { |
| 420 | + // This test serves as an integration test to ensure parallelSort completes |
| 421 | + // correctly when running under the jobserver strategy. It doesn't directly |
| 422 | + // measure concurrency but verifies correctness. |
473 | 423 | const int NumExplicitJobs = 3; |
474 | 424 | startMakeProxy(NumExplicitJobs); |
475 | 425 |
|
476 | 426 | parallel::strategy = jobserver_concurrency(); |
477 | 427 |
|
478 | 428 | std::vector<int> V(1024); |
| 429 | + // Fill with random data |
479 | 430 | std::mt19937 randEngine; |
480 | 431 | std::uniform_int_distribution<int> dist; |
481 | 432 | for (int &i : V) |
|
0 commit comments