blob: 35a501957445a4aee27907d2b22ea246e5821a7c [file] [log] [blame]
# Copyright 2022 The IREE Authors
#
# Licensed under the Apache License v2.0 with LLVM Exceptions.
# See https://llvm.org/LICENSE.txt for license information.
# SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
"""Rules for running lit tests with the upstream lit binary."""
# This exists as a separate file from iree_lit_test.bzl because we anticipate
# upstreaming it soon.
load("@bazel_skylib//lib:paths.bzl", "paths")
load(":native_binary.bzl", "native_test")
def _tools_on_path_impl(ctx):
runfiles = ctx.runfiles()
# For Bazel 4.x support. Drop when Bazel 4.x is no longer supported
to_merge = [d[DefaultInfo].default_runfiles for d in ctx.attr.srcs]
if hasattr(runfiles, "merge_all"):
runfiles = runfiles.merge_all(to_merge)
else:
for m in to_merge:
runfiles = runfiles.merge(m)
runfiles_symlinks = {}
for src in ctx.attr.srcs:
exe = src[DefaultInfo].files_to_run.executable
if not exe:
fail("All targets used as tools by lit tests must have exactly one" +
" executable, but {} has none".format(src))
bin_path = paths.join(ctx.attr.bin_dir, exe.basename)
if bin_path in runfiles_symlinks:
fail("All tools used by lit tests must have unique basenames, as" +
" they are added to the path." +
" {} and {} conflict".format(runfiles_symlinks[bin_path], exe))
runfiles_symlinks[bin_path] = exe
return [
DefaultInfo(runfiles = ctx.runfiles(
symlinks = runfiles_symlinks,
).merge(runfiles)),
]
_tools_on_path = rule(
_tools_on_path_impl,
attrs = {
"srcs": attr.label_list(allow_files = True, mandatory = True),
"bin_dir": attr.string(mandatory = True),
},
doc = "Symlinks srcs into a single lit_bin directory. All basenames must be unique.",
)
def lit_test(
name,
test_file,
cfg,
tools = None,
args = None,
data = None,
visibility = None,
env = None,
timeout = None,
**kwargs):
"""Runs a single test file with LLVM's lit tool.
Args:
name: string. the name of the generated test target.
test_file: label. The file on which to run lit.
cfg: label. The lit config file. It must list the file extension of
`test_file` in config.suffixes and must be in a parent directory of
`test_file`.
tools: label list. Tools invoked in the lit RUN lines. These binaries will
be symlinked into a directory which is on the path. They must therefore
have unique basenames.
args: string list. Additional arguments to pass to lit. Note that the test
file, `-v`, and a `--path` argument for the directory to which `tools`
are symlinked are added automatically.
data: label list. Additional data dependencies of the test. Note that
targets in `cfg` and `tools`, as well as their data dependencies, are
added automatically.
visibility: visibility of the generated test target.
env: string_dict. Environment variables available during test execution.
See the common Bazel test attribute.
timeout: bazel test timeout string, as per common bazel definitions.
**kwargs: additional keyword arguments to pass to all generated rules.
See https://llvm.org/docs/CommandGuide/lit.html for details on lit
"""
args = args or []
data = data or []
tools = tools or []
tools_on_path_target_name = "_{}_tools_on_path".format(name)
bin_dir = paths.join(
native.package_name(),
tools_on_path_target_name,
"lit_bin",
)
_tools_on_path(
name = tools_on_path_target_name,
testonly = True,
srcs = tools,
bin_dir = bin_dir,
visibility = ["//visibility:private"],
**kwargs
)
native_test(
name = name,
src = "@llvm-project//llvm:lit",
# out = name,
args = [
"-v",
"--path",
bin_dir,
"$(location {})".format(test_file),
] + args,
data = [test_file, cfg, tools_on_path_target_name] + data,
visibility = visibility,
env = env,
timeout = timeout,
**kwargs
)
def lit_test_suite(
name,
srcs,
cfg,
tools = None,
args = None,
data = None,
visibility = None,
size = "small",
env = None,
timeout = None,
**kwargs):
"""Creates one lit test per source file and a test suite that bundles them.
Args:
name: string. the name of the generated test suite.
srcs: label_list. The files which contain the lit tests.
cfg: label. The lit config file. It must list the file extension of
the files in `srcs` in config.suffixes and must be in a parent directory
of `srcs`.
tools: label list. Tools invoked in the lit RUN lines. These binaries will
be symlinked into a directory which is on the path. They must therefore
have unique basenames.
args: string list. Additional arguments to pass to lit. Note that the test
file, `-v`, and a `--path` argument for the directory to which `tools`
are symlinked are added automatically.
data: label list. Additional data dependencies of the test. Note that
targets in `cfg` and `tools`, as well as their data dependencies, are
added automatically.
visibility: visibility of the generated test targets and test suite.
size: string. size of the generated tests.
env: string_dict. Environment variables available during test execution.
See the common Bazel test attribute.
timeout: timeout argument passed to the individual tests.
**kwargs: additional keyword arguments to pass to all generated rules.
See https://llvm.org/docs/CommandGuide/lit.html for details on lit
"""
# If there are kwargs that need to be passed to only some of the generated
# rules, they should be extracted into separate named arguments.
args = args or []
data = data or []
tools = tools or []
tests = []
for test_file in srcs:
# It's generally good practice to prefix any generated names with the
# macro name, but it's also nice to have the test name just match the
# file name.
test_name = "%s.test" % (test_file)
tests.append(test_name)
lit_test(
name = test_name,
test_file = test_file,
cfg = cfg,
tools = tools,
args = args,
data = data,
visibility = visibility,
env = env,
timeout = timeout,
**kwargs
)
native.test_suite(
name = name,
tests = tests,
**kwargs
)