Skip to content

Commit a407c2a

Browse files
committed
support PGO on custom project
1 parent dd9a7bf commit a407c2a

File tree

1 file changed

+51
-29
lines changed

1 file changed

+51
-29
lines changed

src/ci/stage-build.py

+51-29
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,7 @@
1818
import urllib.request
1919
from io import StringIO
2020
from pathlib import Path
21+
from enum import Enum, unique
2122
from typing import Callable, ContextManager, Dict, Iterable, Iterator, List, Optional, \
2223
Tuple, Union
2324

@@ -48,7 +49,6 @@
4849

4950
LLVM_BOLT_CRATES = LLVM_PGO_CRATES
5051

51-
5252
class Pipeline:
5353
# Paths
5454
def checkout_path(self) -> Path:
@@ -451,6 +451,42 @@ def cmd(
451451
)
452452
return subprocess.run(args, env=environment, check=True)
453453

454+
class BenchmarkRunner:
455+
def run_rustc(self, pipeline: Pipeline):
456+
raise NotImplementedError
457+
458+
def run_llvm(self, pipeline: Pipeline):
459+
raise NotImplementedError
460+
461+
def run_bolt(self, pipeline: Pipeline):
462+
raise NotImplementedError
463+
464+
class DefaultBenchmarkRunner(BenchmarkRunner):
465+
def run_rustc(self, pipeline: Pipeline):
466+
run_compiler_benchmarks(
467+
pipeline,
468+
profiles=["Check", "Debug", "Opt"],
469+
scenarios=["All"],
470+
crates=RUSTC_PGO_CRATES,
471+
env=dict(
472+
LLVM_PROFILE_FILE=str(pipeline.rustc_profile_template_path())
473+
)
474+
)
475+
def run_llvm(self, pipeline: Pipeline):
476+
run_compiler_benchmarks(
477+
pipeline,
478+
profiles=["Debug", "Opt"],
479+
scenarios=["Full"],
480+
crates=LLVM_PGO_CRATES
481+
)
482+
483+
def run_bolt(self, pipeline: Pipeline):
484+
run_compiler_benchmarks(
485+
pipeline,
486+
profiles=["Check", "Debug", "Opt"],
487+
scenarios=["Full"],
488+
crates=LLVM_BOLT_CRATES
489+
)
454490

455491
def run_compiler_benchmarks(
456492
pipeline: Pipeline,
@@ -580,14 +616,10 @@ def create_pipeline() -> Pipeline:
580616
raise Exception(f"Optimized build is not supported for platform {sys.platform}")
581617

582618

583-
def gather_llvm_profiles(pipeline: Pipeline):
619+
def gather_llvm_profiles(pipeline: Pipeline, runner: BenchmarkRunner):
584620
LOGGER.info("Running benchmarks with PGO instrumented LLVM")
585-
run_compiler_benchmarks(
586-
pipeline,
587-
profiles=["Debug", "Opt"],
588-
scenarios=["Full"],
589-
crates=LLVM_PGO_CRATES
590-
)
621+
622+
runner.run_llvm(pipeline)
591623

592624
profile_path = pipeline.llvm_profile_merged_file()
593625
LOGGER.info(f"Merging LLVM PGO profiles to {profile_path}")
@@ -609,20 +641,12 @@ def gather_llvm_profiles(pipeline: Pipeline):
609641
delete_directory(pipeline.llvm_profile_dir_root())
610642

611643

612-
def gather_rustc_profiles(pipeline: Pipeline):
644+
def gather_rustc_profiles(pipeline: Pipeline, runner: BenchmarkRunner):
613645
LOGGER.info("Running benchmarks with PGO instrumented rustc")
614646

615647
# Here we're profiling the `rustc` frontend, so we also include `Check`.
616648
# The benchmark set includes various stress tests that put the frontend under pressure.
617-
run_compiler_benchmarks(
618-
pipeline,
619-
profiles=["Check", "Debug", "Opt"],
620-
scenarios=["All"],
621-
crates=RUSTC_PGO_CRATES,
622-
env=dict(
623-
LLVM_PROFILE_FILE=str(pipeline.rustc_profile_template_path())
624-
)
625-
)
649+
runner.run_rustc(pipeline)
626650

627651
profile_path = pipeline.rustc_profile_merged_file()
628652
LOGGER.info(f"Merging Rustc PGO profiles to {profile_path}")
@@ -644,14 +668,10 @@ def gather_rustc_profiles(pipeline: Pipeline):
644668
delete_directory(pipeline.rustc_profile_dir_root())
645669

646670

647-
def gather_llvm_bolt_profiles(pipeline: Pipeline):
671+
def gather_llvm_bolt_profiles(pipeline: Pipeline, runner: BenchmarkRunner):
648672
LOGGER.info("Running benchmarks with BOLT instrumented LLVM")
649-
run_compiler_benchmarks(
650-
pipeline,
651-
profiles=["Check", "Debug", "Opt"],
652-
scenarios=["Full"],
653-
crates=LLVM_BOLT_CRATES
654-
)
673+
674+
runner.run_bolt(pipeline)
655675

656676
merged_profile_path = pipeline.llvm_bolt_profile_merged_file()
657677
profile_files_path = Path("/tmp/prof.fdata")
@@ -744,7 +764,7 @@ def record_metrics(pipeline: Pipeline, timer: Timer):
744764
log_metrics(metrics)
745765

746766

747-
def execute_build_pipeline(timer: Timer, pipeline: Pipeline, final_build_args: List[str]):
767+
def execute_build_pipeline(timer: Timer, pipeline: Pipeline, runner: BenchmarkRunner, final_build_args: List[str]):
748768
# Clear and prepare tmp directory
749769
shutil.rmtree(pipeline.opt_artifacts(), ignore_errors=True)
750770
os.makedirs(pipeline.opt_artifacts(), exist_ok=True)
@@ -762,7 +782,7 @@ def execute_build_pipeline(timer: Timer, pipeline: Pipeline, final_build_args: L
762782
record_metrics(pipeline, rustc_build)
763783

764784
with stage1.section("Gather profiles"):
765-
gather_llvm_profiles(pipeline)
785+
gather_llvm_profiles(pipeline, runner)
766786
print_free_disk_space(pipeline)
767787

768788
clear_llvm_files(pipeline)
@@ -781,7 +801,7 @@ def execute_build_pipeline(timer: Timer, pipeline: Pipeline, final_build_args: L
781801
record_metrics(pipeline, rustc_build)
782802

783803
with stage2.section("Gather profiles"):
784-
gather_rustc_profiles(pipeline)
804+
gather_rustc_profiles(pipeline, runner)
785805
print_free_disk_space(pipeline)
786806

787807
clear_llvm_files(pipeline)
@@ -804,7 +824,7 @@ def execute_build_pipeline(timer: Timer, pipeline: Pipeline, final_build_args: L
804824
record_metrics(pipeline, rustc_build)
805825

806826
with stage3.section("Gather profiles"):
807-
gather_llvm_bolt_profiles(pipeline)
827+
gather_llvm_bolt_profiles(pipeline, runner)
808828

809829
# LLVM is not being cleared here, we want to reuse the previous build
810830
print_free_disk_space(pipeline)
@@ -832,6 +852,8 @@ def execute_build_pipeline(timer: Timer, pipeline: Pipeline, final_build_args: L
832852

833853
timer = Timer()
834854
pipeline = create_pipeline()
855+
runner = DefaultBenchmarkRunner(BenchmarkRunner)
856+
835857
try:
836858
execute_build_pipeline(timer, pipeline, build_args)
837859
except BaseException as e:

0 commit comments

Comments
 (0)