Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
9 changes: 7 additions & 2 deletions devops/scripts/benchmarks/CONTRIB.md
Original file line number Diff line number Diff line change
Expand Up @@ -191,12 +191,17 @@ The benchmark suite generates an interactive HTML dashboard that visualizes `Res

## Utilities

* **`git_project.GitProject`:** Manages git repository cloning, building, and installation for benchmark suites:
* Automatically clones repositories to a specified directory and checks out specific commits/refs.
* Provides standardized directory structure with `src_dir`, `build_dir`, and `install_dir` properties.
* Handles incremental updates - only re-clones if the target commit has changed.
* Supports force rebuilds and custom directory naming via constructor options.
* Provides `configure()`, `build()`, and `install()` methods for CMake-based projects.
* Use this for benchmark suites that need to build from external git repositories (e.g., `ComputeBench`, `VelocityBench`).
* **`utils.utils`:** Provides common helper functions:
* `run()`: Executes shell commands with environment setup (SYCL paths, LD_LIBRARY_PATH).
* `git_clone()`: Clones/updates Git repositories.
* `download()`: Downloads files via HTTP, checks checksums, optionally extracts tar/gz archives.
* `prepare_workdir()`: Sets up the main working directory.
* `create_build_path()`: Creates a clean build directory.
* **`utils.oneapi`:** Provides the `OneAPI` singleton class (`get_oneapi()`). Downloads and installs specified oneAPI components (oneDNN, oneMKL) into the working directory if needed, providing access to their paths (libs, includes, CMake configs). Use this if your benchmark depends on these components instead of requiring a system-wide install.
* **`options.py`:** Defines and holds global configuration options, populated by `argparse` in `main.py`. Use options instead of defining your own global variables.
* **`presets.py`:** Defines named sets of suites (`enabled_suites()`) used by the `--preset` argument.
9 changes: 4 additions & 5 deletions devops/scripts/benchmarks/benches/base.py
Original file line number Diff line number Diff line change
Expand Up @@ -49,8 +49,7 @@ class TracingType(Enum):


class Benchmark(ABC):
def __init__(self, directory, suite):
self.directory = directory
def __init__(self, suite):
self.suite = suite

@abstractmethod
Expand Down Expand Up @@ -84,8 +83,8 @@ def tracing_enabled(self, run_trace, force_trace, tr_type: TracingType):
"""Returns whether tracing is enabled for the given type."""
return (self.traceable(tr_type) or force_trace) and run_trace == tr_type

@abstractmethod
def setup(self):
"""Extra setup steps to be performed before running the benchmark."""
pass

@abstractmethod
Expand Down Expand Up @@ -205,9 +204,9 @@ def run_bench(

def create_data_path(self, name, skip_data_dir=False):
if skip_data_dir:
data_path = os.path.join(self.directory, name)
data_path = os.path.join(options.workdir, name)
else:
data_path = os.path.join(self.directory, "data", name)
data_path = os.path.join(options.workdir, "data", name)
if options.redownload and Path(data_path).exists():
shutil.rmtree(data_path)

Expand Down
57 changes: 28 additions & 29 deletions devops/scripts/benchmarks/benches/benchdnn.py
Original file line number Diff line number Diff line change
Expand Up @@ -8,19 +8,16 @@

from .base import Suite, Benchmark, TracingType
from options import options
from utils.utils import git_clone, run, create_build_path
from utils.result import Result
from utils.oneapi import get_oneapi
from utils.logger import log
from .benchdnn_list import get_bench_dnn_list
from git_project import GitProject


class OneDnnBench(Suite):
def __init__(self, directory):
self.directory = Path(directory).resolve()
build_path = create_build_path(self.directory, "onednn-build")
self.build_dir = Path(build_path)
self.src_dir = self.directory / "onednn-repo"
def __init__(self):
self.project = None

def git_url(self):
return "https://github.com/uxlfoundation/oneDNN.git"
Expand Down Expand Up @@ -62,36 +59,35 @@ def setup(self) -> None:
if options.sycl is None:
return

self.src_dir = git_clone(
self.directory,
"onednn-repo",
self.git_url(),
self.git_tag(),
)

self.oneapi = get_oneapi()
cmake_args = [
"cmake",
f"-S {self.src_dir}",
f"-B {self.build_dir}",
if self.project is None:
self.project = GitProject(
self.git_url(),
self.git_tag(),
Path(options.workdir),
"onednn",
force_rebuild=True,
)

extra_cmake_args = [
f"-DCMAKE_PREFIX_PATH={options.sycl}",
"-DCMAKE_CXX_COMPILER=clang++",
"-DCMAKE_C_COMPILER=clang",
"-DCMAKE_BUILD_TYPE=Release",
"-DDNNL_BUILD_TESTS=ON",
"-DDNNL_BUILD_EXAMPLES=OFF",
"-DDNNL_CPU_RUNTIME=NONE", # Disable SYCL CPU support
"-DDNNL_GPU_RUNTIME=SYCL", # Enable SYCL GPU support
]
run(
cmake_args,
self.project.configure(
extra_cmake_args,
install_prefix=False,
add_sycl=True,
)

run(
f"cmake --build {self.build_dir} --target benchdnn -j {options.build_jobs}",
self.project.build(
target="benchdnn",
add_sycl=True,
ld_library=[str(self.build_dir) + "/src"] + self.oneapi.ld_libraries(),
ld_library=[str(self.project.build_dir / "src")]
+ self.oneapi.ld_libraries(),
timeout=60 * 20,
)

Expand All @@ -113,7 +109,10 @@ def __init__(self, suite, bench_driver, bench_name, bench_args, syclgraph=True):
self.bench_args += " --execution-mode=direct"
self.bench_name += "-eager"
self.bench_args += f" {bench_args}"
self.bench_bin = suite.build_dir / "tests" / "benchdnn" / "benchdnn"

@property
def benchmark_bin(self) -> Path:
return self.suite.project.build_dir / "tests" / "benchdnn" / "benchdnn"

def enabled(self):
if options.sycl is None:
Expand All @@ -129,8 +128,8 @@ def explicit_group(self) -> str:
return self.exp_group

def setup(self):
if not self.bench_bin.exists():
raise FileNotFoundError(f"Benchmark binary not found: {self.bench_bin}")
if not self.benchmark_bin.exists():
raise FileNotFoundError(f"Benchmark binary not found: {self.benchmark_bin}")

def run(
self,
Expand All @@ -145,12 +144,12 @@ def run(
extra_trace_opt = None

command = [
str(self.bench_bin),
str(self.benchmark_bin),
*self.bench_args.split(),
]

ld_library = self.suite.oneapi.ld_libraries() + [
str(self.suite.build_dir / "src")
str(self.suite.project.build_dir / "src")
]

env_vars = dict(env_vars) if env_vars else {}
Expand Down
59 changes: 24 additions & 35 deletions devops/scripts/benchmarks/benches/compute.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,18 +4,18 @@
# SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception

from itertools import product
import os
import csv
import io
import copy
import math
from enum import Enum
from pathlib import Path

from utils.utils import run, git_clone, create_build_path
from .base import Benchmark, Suite, TracingType
from utils.result import BenchmarkMetadata, Result
from .base import Benchmark, Suite
from options import options
from git_project import GitProject


class RUNTIMES(Enum):
Expand Down Expand Up @@ -49,9 +49,9 @@ def runtime_to_tag_name(runtime: RUNTIMES) -> str:


class ComputeBench(Suite):
def __init__(self, directory):
self.directory = directory
def __init__(self):
self.submit_graph_num_kernels = [4, 10, 32]
self.project = None

def name(self) -> str:
return "Compute Benchmarks"
Expand All @@ -66,47 +66,36 @@ def setup(self) -> None:
if options.sycl is None:
return

repo_path = git_clone(
self.directory,
"compute-benchmarks-repo",
self.git_url(),
self.git_hash(),
)
build_path = create_build_path(self.directory, "compute-benchmarks-build")
if self.project is None:
self.project = GitProject(
self.git_url(),
self.git_hash(),
Path(options.workdir),
"compute-benchmarks",
force_rebuild=True,
)

configure_command = [
"cmake",
f"-B {build_path}",
f"-S {repo_path}",
f"-DCMAKE_BUILD_TYPE=Release",
extra_args = [
f"-DBUILD_SYCL=ON",
f"-DSYCL_COMPILER_ROOT={options.sycl}",
f"-DALLOW_WARNINGS=ON",
f"-DCMAKE_CXX_COMPILER=clang++",
f"-DCMAKE_C_COMPILER=clang",
]

if options.ur_adapter == "cuda":
configure_command += [
extra_args += [
"-DBUILD_SYCL_WITH_CUDA=ON",
"-DBUILD_L0=OFF",
"-DBUILD_OCL=OFF",
]

if options.ur is not None:
configure_command += [
extra_args += [
f"-DBUILD_UR=ON",
f"-Dunified-runtime_DIR={options.ur}/lib/cmake/unified-runtime",
]

run(configure_command, add_sycl=True)

run(
f"cmake --build {build_path} -j {options.build_jobs}",
add_sycl=True,
)

self.built = True
self.project.configure(extra_args, install_prefix=False, add_sycl=True)
self.project.build(add_sycl=True)

def additional_metadata(self) -> dict[str, BenchmarkMetadata]:
metadata = {
Expand Down Expand Up @@ -370,7 +359,7 @@ def __init__(
runtime: RUNTIMES = None,
profiler_type: PROFILERS = PROFILERS.TIMER,
):
super().__init__(bench.directory, bench)
super().__init__(bench)
self.bench = bench
self.bench_name = name
self.test = test
Expand All @@ -384,6 +373,11 @@ def __init__(
self._validate_attr("iterations_regular")
self._validate_attr("iterations_trace")

@property
def benchmark_bin(self) -> Path:
"""Returns the path to the benchmark binary"""
return self.bench.project.build_dir / "bin" / self.bench_name

def get_iters(self, run_trace: TracingType):
"""Returns the number of iterations to run for the given tracing type."""
return (
Expand Down Expand Up @@ -437,11 +431,6 @@ def bin_args(self, run_trace: TracingType = TracingType.NONE) -> list[str]:
def extra_env_vars(self) -> dict:
return {}

def setup(self):
self.benchmark_bin = os.path.join(
self.bench.directory, "compute-benchmarks-build", "bin", self.bench_name
)

def explicit_group(self):
return ""

Expand All @@ -455,7 +444,7 @@ def run(
force_trace: bool = False,
) -> list[Result]:
command = [
f"{self.benchmark_bin}",
str(self.benchmark_bin),
f"--test={self.test}",
"--csv",
"--noHeaders",
Expand Down
Loading
Loading