From a62c35ffa8822ed4a071f77b108f0522717b7084 Mon Sep 17 00:00:00 2001 From: cloudhan Date: Thu, 23 Mar 2023 21:47:32 +0800 Subject: [PATCH 01/43] Add ci docs gen and github pages pub (#73) Add documentation geneartion and publishing CI. Following, all paths are assumed in /docs/ Basics logic is as in build-docs.sh for non-CI case: 1. compose the docs/ dir for mkdocs (mkdocs-material, specifically) 2. mkdocs build generate non-versioned site/ 3. copy site/ to generated/ 4. patch generated/ by creating generated/index.html for non version URL redirection and generate versions.json for the version drop down list In CI, 1,2 are in docs build stage and the stage driven by as matrix what version we want to publish to the site 3,4 is publish stage. Two stages are linked together by artifacts upload and download. --- .github/workflows/docs-tests.yaml | 32 ------------ .github/workflows/github-pages.yaml | 79 +++++++++++++++++++++++++++++ docs/.gitignore | 3 ++ docs/BUILD.bazel | 19 +++++-- docs/build-docs.sh | 44 ++++++++++++++++ docs/mkdocs.yaml | 30 +++++++++++ docs/mkdocs/stylesheets/extra.css | 3 ++ docs/requirements.txt | 1 + docs/versioning.py | 72 ++++++++++++++++++++++++++ 9 files changed, 247 insertions(+), 36 deletions(-) delete mode 100644 .github/workflows/docs-tests.yaml create mode 100644 .github/workflows/github-pages.yaml create mode 100644 docs/.gitignore create mode 100755 docs/build-docs.sh create mode 100644 docs/mkdocs.yaml create mode 100644 docs/mkdocs/stylesheets/extra.css create mode 100644 docs/requirements.txt create mode 100644 docs/versioning.py diff --git a/.github/workflows/docs-tests.yaml b/.github/workflows/docs-tests.yaml deleted file mode 100644 index c631cb36..00000000 --- a/.github/workflows/docs-tests.yaml +++ /dev/null @@ -1,32 +0,0 @@ -name: Test Generating Docs - -on: - push: - branches: - - main - pull_request: - -jobs: - test: - name: "Test Generating Docs" - runs-on: ubuntu-20.04 - defaults: - run: - working-directory: ./docs - timeout-minutes: 60 - steps: - - uses: actions/checkout@v3 - - - uses: bazelbuild/setup-bazelisk@v2 - - - name: Mount bazel cache - uses: actions/cache@v3 - with: - path: ~/.cache/bazel - key: bazel-gen-docs - - - run: bazelisk build -- //... - - - run: ls bazel-bin - - - run: bazelisk shutdown diff --git a/.github/workflows/github-pages.yaml b/.github/workflows/github-pages.yaml new file mode 100644 index 00000000..f2acc1b7 --- /dev/null +++ b/.github/workflows/github-pages.yaml @@ -0,0 +1,79 @@ +name: Generate docs + +on: + pull_request: + branches: + - main + push: + branches: + - main + +jobs: + pages: + runs-on: ubuntu-latest + strategy: + matrix: + docs: + # { ref: , name: } + - { ref: main, name: latest } + steps: + - uses: actions/checkout@v3 + if: ${{ matrix.docs.ref == 'main' }} + - uses: actions/checkout@v3 + with: + ref: ${{ matrix.docs.ref }} + if: ${{ matrix.docs.ref != 'main' }} + + - uses: bazelbuild/setup-bazelisk@v2 + - name: Mount bazel cache + uses: actions/cache@v3 + with: + path: ~/.cache/bazel + key: bazel-gen-docs-${{ matrix.docs.ref }} + + - uses: actions/setup-python@v4 + with: + python-version: "3.10" + cache: pip + + - name: Generate docs + run: bash ./build-docs.sh + env: + CI: 1 + working-directory: ${{ github.workspace }}/docs + + - run: bazelisk shutdown + + - uses: actions/upload-artifact@v3 + with: + name: "${{ matrix.docs.name }}" + path: ${{ github.workspace }}/docs/site/ + if-no-files-found: error + if: ${{ github.event_name != 'pull_request' }} + + publish: + needs: pages + if: ${{ github.event_name != 'pull_request' }} + runs-on: ubuntu-latest + steps: + - uses: actions/checkout@v3 + + - uses: actions/download-artifact@v3 + with: + path: ${{ github.workspace }}/docs/generated + - name: Inspect docs site directory structure + run: find ${{ github.workspace }}/docs/generated -maxdepth 2 + + - uses: actions/setup-python@v4 + with: + python-version: "3.10" + - run: | + pip install packaging==23.* + python versioning.py generated/ + working-directory: ${{ github.workspace }}/docs + + - uses: peaceiris/actions-gh-pages@v3 + with: + github_token: ${{ secrets.GITHUB_TOKEN }} + publish_dir: ./docs/generated + force_orphan: true diff --git a/docs/.gitignore b/docs/.gitignore new file mode 100644 index 00000000..8bac8abf --- /dev/null +++ b/docs/.gitignore @@ -0,0 +1,3 @@ +docs/ +generated/ +site/ diff --git a/docs/BUILD.bazel b/docs/BUILD.bazel index ea3c8df0..417a2191 100644 --- a/docs/BUILD.bazel +++ b/docs/BUILD.bazel @@ -1,29 +1,40 @@ load("@io_bazel_stardoc//stardoc:stardoc.bzl", "stardoc") +# NOTE: when the `out` is changed, the `nav` part of `mkdocs.yaml` must be also be changed correspondingly. stardoc( name = "user_docs", - out = "user_docs.md", + out = "user/user_docs.md", input = "user_docs.bzl", deps = ["@rules_cuda//:bzl_srcs"], ) stardoc( name = "toolchain_config_docs", - out = "toolchain_config_docs.md", + out = "user/toolchain_config_docs.md", input = "toolchain_config_docs.bzl", deps = ["@rules_cuda//:bzl_srcs"], ) stardoc( name = "providers_docs", - out = "providers_docs.md", + out = "developer/providers_docs.md", input = "providers_docs.bzl", deps = ["@rules_cuda//:bzl_srcs"], ) stardoc( name = "developer_docs", - out = "developer_docs.md", + out = "developer/developer_docs.md", input = "developer_docs.bzl", deps = ["@rules_cuda//:bzl_srcs"], ) + +filegroup( + name = "all_docs", + srcs = [ + ":developer_docs", + ":providers_docs", + ":toolchain_config_docs", + ":user_docs", + ], +) diff --git a/docs/build-docs.sh b/docs/build-docs.sh new file mode 100755 index 00000000..644d8d74 --- /dev/null +++ b/docs/build-docs.sh @@ -0,0 +1,44 @@ +#!/bin/bash + +function prepare-env { + pip install -r requirements.txt +} + +function compose-docs { + rm -rf docs site + mkdir -p docs + cp ../README.md docs/index.md + bazel build :all_docs + rsync -a --prune-empty-dirs --include '*/' mkdocs/stylesheets docs/ + rsync -a --prune-empty-dirs --include '*/' --include '*.md' --exclude '*' bazel-bin/ docs/ +} + +function compose-versioned-site { + mkdir -p generated + rsync -a --prune-empty-dirs --include '*/' site/ generated/$1/ + python versioning.py generated/ --force + + printf "\nRun following command to update version list then serve locally:\n\n" + printf "\tpython -m http.server -d generate/\n\n" +} + + +CI=${CI:-0} # 1 for CI only logic + +if [ $CI == "1" ]; then + set -ex + prepare-env + compose-docs + mkdocs build +else + if [[ $# -ne 1 ]]; then + printf "Usage: $0 \n" + exit -1 + fi + version=$1 + + # env should be prepared manually + compose-docs + mkdocs build + compose-versioned-site $version +fi diff --git a/docs/mkdocs.yaml b/docs/mkdocs.yaml new file mode 100644 index 00000000..4ee425df --- /dev/null +++ b/docs/mkdocs.yaml @@ -0,0 +1,30 @@ +site_name: "rules_cuda: Starlark implementation of bazel rules for CUDA" +repo_url: https://github.com/bazel-contrib/rules_cuda +docs_dir: docs + +theme: + name: material + palette: + - media: "(prefers-color-scheme: light)" + scheme: default + primary: green + locale: en + features: + - navigation.tabs +extra_css: + - stylesheets/extra.css + +extra: + version: + # we are not actually using mike + # just for `versions.json` to be functional + provider: mike + +nav: + - Home: index.md + - User: + - Using the rules: user/user_docs.md + - Configure the toolchain: user/toolchain_config_docs.md + - Developer: + - Providers: developer/providers_docs.md + - Rule Authoring: developer/developer_docs.md diff --git a/docs/mkdocs/stylesheets/extra.css b/docs/mkdocs/stylesheets/extra.css new file mode 100644 index 00000000..4d243364 --- /dev/null +++ b/docs/mkdocs/stylesheets/extra.css @@ -0,0 +1,3 @@ +.md-header { + background: #44a147 +} diff --git a/docs/requirements.txt b/docs/requirements.txt new file mode 100644 index 00000000..b8c65086 --- /dev/null +++ b/docs/requirements.txt @@ -0,0 +1 @@ +mkdocs-material==9.1.3 diff --git a/docs/versioning.py b/docs/versioning.py new file mode 100644 index 00000000..053fefe8 --- /dev/null +++ b/docs/versioning.py @@ -0,0 +1,72 @@ +import argparse +import json +import os +from packaging.version import parse as parse_version + +TEMPLATE = """ + + + + + + Redirecting + + + + + Redirecting to {version}/... + + +""" + + +def collect_versions(work_dir): + versioned_dirs = [item.name for item in os.scandir(work_dir) if item.is_dir()] + names = [] + versions = [] + for v in versioned_dirs: + try: + parse_version(v) + versions.append(v) + except: + names.append(v) + + versions.sort(key=lambda v: parse_version(v), reverse=True) + names.sort() + return versions + names + + +def generate_redirect_page(work_dir, version, *, force=False): + output = os.path.join(work_dir, "index.html") + assert force or not os.path.exists(output) + with open(output, "w") as f: + f.write(TEMPLATE.format(version=version)) + + +def generate_version_json(work_dir, versions, *, force=False): + output = os.path.join(work_dir, "versions.json") + assert force or not os.path.exists(output) + with open(output, "w") as f: + json.dump([{"version": v, "title": v, "aliases": []} for v in versions], f) + + +def process(work_dir, default_version=None, *, force=False): + versions = collect_versions(work_dir) + if default_version is None: + default_version = versions[0] + generate_redirect_page(work_dir, default_version, force=force) + generate_version_json(work_dir, versions, force=force) + + +if __name__ == "__main__": + parser = argparse.ArgumentParser() + parser.add_argument("work_dir") + parser.add_argument("--default_version", "-d", default=None) + parser.add_argument("--force", "-f", action="store_true") + args = parser.parse_args() + + process(args.work_dir, args.default_version, force=args.force) From f2aed5e4c0cde0701ace71c7b59df643a92b8784 Mon Sep 17 00:00:00 2001 From: cloudhan Date: Fri, 24 Mar 2023 00:05:53 +0800 Subject: [PATCH 02/43] Change building test combination (#75) * Linearize combinations from product(os, cuda-version) for fine-grind control * Remove windows cuda 11.2.2 * More combinations for linux --- .github/workflows/build-tests.yaml | 45 +++++++++++++++++------------- 1 file changed, 25 insertions(+), 20 deletions(-) diff --git a/.github/workflows/build-tests.yaml b/.github/workflows/build-tests.yaml index 290f796e..5a2ae3b4 100644 --- a/.github/workflows/build-tests.yaml +++ b/.github/workflows/build-tests.yaml @@ -8,58 +8,63 @@ on: jobs: test: - name: "Test Examples Build (CUDA ${{ matrix.cuda-version }} on ${{ matrix.os }})" - runs-on: ${{ matrix.os }} + name: "Test Examples Build (CUDA ${{ matrix.cases.cuda-version }} on ${{ matrix.cases.os }})" + runs-on: ${{ matrix.cases.os }} timeout-minutes: 60 strategy: matrix: - os: - - ubuntu-18.04 - - windows-2019 - cuda-version: - - 10.1.243 - - 11.2.2 - - 11.6.2 + cases: + - { os: "ubuntu-18.04", cuda-version: "10.1.243", source: "nvidia" } + - { os: "ubuntu-18.04", cuda-version: "11.2.2", source: "nvidia" } + - { os: "ubuntu-20.04", cuda-version: "11.6.2", source: "nvidia" } + # - { os: "ubuntu-22.04", cuda-version: "11.5.1-1ubuntu1", source: "ubuntu" } + - { os: "windows-2019", cuda-version: "10.1.243", source: "nvidia" } + - { os: "windows-2019", cuda-version: "11.6.2", source: "nvidia" } steps: - uses: actions/checkout@v3 - uses: bazelbuild/setup-bazelisk@v2 - name: Mount bazel cache - if: ${{ !startsWith(matrix.os, 'windows') }} + if: ${{ !startsWith(matrix.cases.os, 'windows') }} uses: actions/cache@v3 with: path: ~/.cache/bazel - key: bazel-${{ matrix.os }}-cuda-${{ matrix.cuda-version }}-${{ hashFiles('.bazelversion') }} + key: bazel-${{ matrix.cases.os }}-cuda-${{ matrix.cases.cuda-version }}-${{ hashFiles('.bazelversion') }} - - name: Install CUDA (Linux) + - name: Install CUDA (NVIDIA, Linux) uses: Jimver/cuda-toolkit@v0.2.10 - if: ${{ !startsWith(matrix.os, 'windows') }} + if: ${{ !startsWith(matrix.cases.os, 'windows') && matrix.cases.source == 'nvidia' }} with: - cuda: ${{ matrix.cuda-version }} + cuda: ${{ matrix.cases.cuda-version }} sub-packages: '["nvcc", "cudart-dev"]' method: network - - name: Show bin, include, lib (Linux) - if: ${{ !startsWith(matrix.os, 'windows') }} + - name: Show bin, include, lib (NVIDIA, Linux) + if: ${{ !startsWith(matrix.cases.os, 'windows') && matrix.cases.source == 'nvidia' }} run: | tree ${CUDA_PATH}/bin tree ${CUDA_PATH}/include tree ${CUDA_PATH}/lib64 + - name: Install CUDA (Ubuntu) + if: ${{ !startsWith(matrix.cases.os, 'windows') && matrix.cases.source == 'ubuntu' }} + run: | + sudo apt-get update + sudo apt-get install -y nvidia-cuda-dev=${{ matrix.cases.cuda-version }} - name: Install CUDA (Windows) uses: Jimver/cuda-toolkit@v0.2.10 - if: ${{ startsWith(matrix.os, 'windows') }} + if: ${{ startsWith(matrix.cases.os, 'windows') }} with: - cuda: ${{ matrix.cuda-version }} + cuda: ${{ matrix.cases.cuda-version }} sub-packages: '["nvcc", "cudart"]' method: network - name: Show bin, include, lib64 (Windows) - if: ${{ startsWith(matrix.os, 'windows') }} + if: ${{ startsWith(matrix.cases.os, 'windows') }} run: | tree /F $env:CUDA_PATH/bin tree /F $env:CUDA_PATH/include tree /F $env:CUDA_PATH/lib/x64 - name: Set Visual Studio Environment (Windows) - if: ${{ startsWith(matrix.os, 'windows') }} + if: ${{ startsWith(matrix.cases.os, 'windows') }} run: .github/workflows/Set-VSEnv.ps1 2019 - run: bazelisk build @rules_cuda_examples//basic:main From 738060e2f05644d9f116257ec9fe86f36a3ed5d4 Mon Sep 17 00:00:00 2001 From: Ethan Steinberg Date: Thu, 23 Mar 2023 18:23:01 -0700 Subject: [PATCH 03/43] Various fixes to get rules_cuda to work with Lambda-stack (#74) --- .github/workflows/build-tests.yaml | 8 ++++++-- cuda/private/repositories.bzl | 13 ++++++++++++- 2 files changed, 18 insertions(+), 3 deletions(-) diff --git a/.github/workflows/build-tests.yaml b/.github/workflows/build-tests.yaml index 5a2ae3b4..75c8415f 100644 --- a/.github/workflows/build-tests.yaml +++ b/.github/workflows/build-tests.yaml @@ -17,7 +17,7 @@ jobs: - { os: "ubuntu-18.04", cuda-version: "10.1.243", source: "nvidia" } - { os: "ubuntu-18.04", cuda-version: "11.2.2", source: "nvidia" } - { os: "ubuntu-20.04", cuda-version: "11.6.2", source: "nvidia" } - # - { os: "ubuntu-22.04", cuda-version: "11.5.1-1ubuntu1", source: "ubuntu" } + - { os: "ubuntu-22.04", cuda-version: "11.5.1-1ubuntu1", source: "ubuntu" } - { os: "windows-2019", cuda-version: "10.1.243", source: "nvidia" } - { os: "windows-2019", cuda-version: "11.6.2", source: "nvidia" } steps: @@ -48,7 +48,11 @@ jobs: if: ${{ !startsWith(matrix.cases.os, 'windows') && matrix.cases.source == 'ubuntu' }} run: | sudo apt-get update - sudo apt-get install -y nvidia-cuda-dev=${{ matrix.cases.cuda-version }} + sudo apt-get install -y nvidia-cuda-dev=${{ matrix.cases.cuda-version }} nvidia-cuda-toolkit=${{ matrix.cases.cuda-version }} gcc-9 g++-9 + export CC=gcc-9 + export CXX=g++-9 + echo "CC=gcc-9" >> $GITHUB_ENV + echo "CXX=g++-9" >> $GITHUB_ENV - name: Install CUDA (Windows) uses: Jimver/cuda-toolkit@v0.2.10 diff --git a/cuda/private/repositories.bzl b/cuda/private/repositories.bzl index 804a69db..c6596655 100644 --- a/cuda/private/repositories.bzl +++ b/cuda/private/repositories.bzl @@ -44,6 +44,12 @@ def detect_cuda_toolkit(repository_ctx): ptxas_path = repository_ctx.which("ptxas") if ptxas_path: # ${CUDA_PATH}/bin/ptxas + + # Some distributions instead put CUDA binaries in a seperate path + # Manually check and redirect there when necessary + alternative = repository_ctx.path('/usr/lib/nvidia-cuda-toolkit/bin/nvcc') + if str(ptxas_path) == "/usr/bin/ptxas" and alternative.exists: + ptxas_path = alternative cuda_path = str(ptxas_path.dirname.dirname) if cuda_path == None and _is_linux(repository_ctx): cuda_path = "/usr/local/cuda" @@ -98,7 +104,12 @@ def config_cuda_toolkit_and_nvcc(repository_ctx, cuda): defs_bzl_content = "" defs_if_local_cuda = "def if_local_cuda(if_true, if_false = []):\n return %s\n" if cuda.path != None: - repository_ctx.symlink(cuda.path, "cuda") + # When using a special cuda toolkit path install, need to manually fix up the lib64 links + if cuda.path == "/usr/lib/nvidia-cuda-toolkit": + repository_ctx.symlink(cuda.path + "/bin", "cuda/bin") + repository_ctx.symlink("/usr/lib/x86_64-linux-gnu", "cuda/lib64") + else: + repository_ctx.symlink(cuda.path, "cuda") repository_ctx.symlink(Label("//cuda:runtime/BUILD.local_cuda"), "BUILD") defs_bzl_content += defs_if_local_cuda % "if_true" else: From f5dda407d98443b3ec17bba209b92c697e2fe3a6 Mon Sep 17 00:00:00 2001 From: cloudhan Date: Fri, 24 Mar 2023 23:58:16 +0800 Subject: [PATCH 04/43] Decorate docs (#76) * Avoid stardoc preformatted text overflow The preformatted text generated by stardoc is hardcoded to be with max column width equals to 100, and is not configurable. See: https://github.com/bazelbuild/bazel/blob/f8a59d97ac/src/main/java/com/google/devtools/build/skydoc/rendering/MarkdownUtil.java#L35 https://github.com/bazelbuild/skydoc/issues/142 * Better docs format after publishing --- cuda/private/repositories.bzl | 18 ++++++++-------- cuda/private/rules/flags.bzl | 34 +++++++++++++++++-------------- docs/build-docs.sh | 2 ++ docs/mkdocs/stylesheets/extra.css | 17 ++++++++++++++++ 4 files changed, 48 insertions(+), 23 deletions(-) diff --git a/cuda/private/repositories.bzl b/cuda/private/repositories.bzl index c6596655..d420eddc 100644 --- a/cuda/private/repositories.bzl +++ b/cuda/private/repositories.bzl @@ -1,4 +1,4 @@ -"""Generate @local_cuda//""" +"""Generate `@local_cuda//`""" load("@bazel_tools//tools/build_defs/repo:http.bzl", "http_archive") load("@bazel_tools//tools/build_defs/repo:utils.bzl", "maybe") @@ -29,9 +29,10 @@ def detect_cuda_toolkit(repository_ctx): """Detect CUDA Toolkit. The path to CUDA Toolkit is determined as: - - taken from CUDA_PATH environment variable or - - determined through 'which ptxas' or - - defaults to '/usr/local/cuda' + + - taken from `CUDA_PATH` environment variable or + - determined through `which ptxas` or + - defaults to `/usr/local/cuda` Args: repository_ctx: repository_ctx @@ -93,7 +94,7 @@ def detect_cuda_toolkit(repository_ctx): ) def config_cuda_toolkit_and_nvcc(repository_ctx, cuda): - """Generate @local_cuda//BUILD and @local_cuda//defs.bzl and @local_cuda//toolchain/BUILD + """Generate `@local_cuda//BUILD` and `@local_cuda//defs.bzl` and `@local_cuda//toolchain/BUILD` Args: repository_ctx: repository_ctx @@ -141,9 +142,10 @@ def detect_clang(repository_ctx): """Detect local clang installation. The path to clang is determined by: + - taken from `CUDA_CLANG_PATH` environment variable or - - taken from `BAZEL_LLVM` environment variable as `/bin/clang` or - - determined through 'which clang' or + - taken from `BAZEL_LLVM` environment variable as `$BAZEL_LLVM/bin/clang` or + - determined through `which clang` or - treated as being not detected and not configured Args: @@ -167,7 +169,7 @@ def detect_clang(repository_ctx): return clang_path def config_clang(repository_ctx, cuda, clang_path): - """Generate @local_cuda//toolchain/clang/BUILD + """Generate `@local_cuda//toolchain/clang/BUILD` Args: repository_ctx: repository_ctx diff --git a/cuda/private/rules/flags.bzl b/cuda/private/rules/flags.bzl index 7b593c9d..e96957ec 100644 --- a/cuda/private/rules/flags.bzl +++ b/cuda/private/rules/flags.bzl @@ -15,26 +15,30 @@ When passing cuda_archs from commandline, its spec grammar is as follows: ARCH_SPECS ::= ARCH_SPEC [ ';' ARCH_SPECS ] ARCH_SPEC ::= [ VIRTUAL_ARCH ':' ] GPU_ARCHS GPU_ARCHS ::= GPU_ARCH [ ',' GPU_ARCHS ] - GPU_ARCH ::= ( 'sm_' | 'lto_' ) ARCH_NUMBER - | VIRTUAL_ARCH - VIRTUAL_ARCH ::= ( 'compute_' | 'lto_' ) ARCH_NUMBER + GPU_ARCH ::= 'sm_' ARCH_NUMBER + | 'lto_' ARCH_NUMBER + | VIRTUAL_ARCH + VIRTUAL_ARCH ::= 'compute_' ARCH_NUMBER + | 'lto_' ARCH_NUMBER ARCH_NUMBER ::= (a string in predefined cuda_archs list) E.g.: -- compute_80:sm_80,sm_86 - Use compute_80 PTX, generate cubin with sm_80 and sm_86, no PTX embedded -- compute_80:compute_80,sm_80,sm_86 - Use compute_80 PTX, generate cubin with sm_80 and sm_86, PTX embedded -- compute_80:compute_80 - Embed compute_80 PTX, fully relay on ptxas -- sm_80,sm_86 - Same as "compute_80:sm_80,sm_86", the arch with minimum integer value will be automatically populated. -- sm_80;sm_86 - Two specs used. -- compute_80 - Same as "compute_80:compute_80" + +- `compute_80:sm_80,sm_86`: + Use `compute_80` PTX, generate cubin with `sm_80` and `sm_86`, no PTX embedded +- `compute_80:compute_80,sm_80,sm_86`: + Use `compute_80` PTX, generate cubin with `sm_80` and `sm_86`, PTX embedded +- `compute_80:compute_80`: + Embed `compute_80` PTX, fully relay on `ptxas` +- `sm_80,sm_86`: + Same as `compute_80:sm_80,sm_86`, the arch with minimum integer value will be automatically populated. +- `sm_80;sm_86`: + Two specs used. +- `compute_80`: + Same as `compute_80:compute_80` Best Practices: + - Library supports a full range of archs from xx to yy, you should embed the yy PTX - Library supports a sparse range of archs from xx to yy, you should embed the xx PTX""", implementation = _cuda_archs_flag_impl, diff --git a/docs/build-docs.sh b/docs/build-docs.sh index 644d8d74..37e2a7cb 100755 --- a/docs/build-docs.sh +++ b/docs/build-docs.sh @@ -11,6 +11,8 @@ function compose-docs { bazel build :all_docs rsync -a --prune-empty-dirs --include '*/' mkdocs/stylesheets docs/ rsync -a --prune-empty-dirs --include '*/' --include '*.md' --exclude '*' bazel-bin/ docs/ + find docs/ -name '*.md' -exec sed -i 's#
#
#g' {} \;
+    find docs/ -name '*.md' -exec sed -i 's#
#
#g' {} \; } function compose-versioned-site { diff --git a/docs/mkdocs/stylesheets/extra.css b/docs/mkdocs/stylesheets/extra.css index 4d243364..58ac8189 100644 --- a/docs/mkdocs/stylesheets/extra.css +++ b/docs/mkdocs/stylesheets/extra.css @@ -1,3 +1,20 @@ .md-header { background: #44a147 } + +.stardoc-pre { + height: fit-content; + width: inherit; + overflow: auto; + scrollbar-width: thin; + font-size: 0.8em; +} + +.stardoc-pre::-webkit-scrollbar { + height: 0.25em; + width: 0.25em; +} + +.stardoc-pre::-webkit-scrollbar-thumb { + background-color: var(--md-default-fg-color--lighter); +} From c4c018c59bb8440029a1e24d6f4a8723f93e6fa6 Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Fri, 24 Mar 2023 16:53:52 +0000 Subject: [PATCH 05/43] chore(deps): update dependency mkdocs-material to v9.1.4 (#77) Co-authored-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> --- docs/requirements.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/requirements.txt b/docs/requirements.txt index b8c65086..73783653 100644 --- a/docs/requirements.txt +++ b/docs/requirements.txt @@ -1 +1 @@ -mkdocs-material==9.1.3 +mkdocs-material==9.1.4 From 15765b8a970a053d9947e7b5be5e2dbd93b85af4 Mon Sep 17 00:00:00 2001 From: cloudhan Date: Wed, 29 Mar 2023 22:11:52 +0800 Subject: [PATCH 06/43] Stop using ubuntu-18.04 (#80) The Ubuntu-18.04 environment is deprecated and will be removed on April 1st, 2023. --- .github/workflows/build-tests.yaml | 3 +-- .github/workflows/release.yaml | 4 ++-- 2 files changed, 3 insertions(+), 4 deletions(-) diff --git a/.github/workflows/build-tests.yaml b/.github/workflows/build-tests.yaml index 75c8415f..2e39d581 100644 --- a/.github/workflows/build-tests.yaml +++ b/.github/workflows/build-tests.yaml @@ -14,8 +14,7 @@ jobs: strategy: matrix: cases: - - { os: "ubuntu-18.04", cuda-version: "10.1.243", source: "nvidia" } - - { os: "ubuntu-18.04", cuda-version: "11.2.2", source: "nvidia" } + - { os: "ubuntu-20.04", cuda-version: "11.2.2", source: "nvidia" } - { os: "ubuntu-20.04", cuda-version: "11.6.2", source: "nvidia" } - { os: "ubuntu-22.04", cuda-version: "11.5.1-1ubuntu1", source: "ubuntu" } - { os: "windows-2019", cuda-version: "10.1.243", source: "nvidia" } diff --git a/.github/workflows/release.yaml b/.github/workflows/release.yaml index 2ab2d0dc..540c79a6 100644 --- a/.github/workflows/release.yaml +++ b/.github/workflows/release.yaml @@ -15,7 +15,7 @@ jobs: strategy: matrix: os: - - ubuntu-18.04 + - ubuntu-22.04 cuda-version: - 11.6.2 steps: @@ -71,4 +71,4 @@ jobs: upload_url: ${{ steps.rules_cuda_release.outputs.upload_url }} asset_name: rules_cuda-${{ env.RELEASE_VERSION }}.tar.gz asset_path: ${{ github.workspace }}/.github/rules_cuda.tar.gz - asset_content_type: application/gzip \ No newline at end of file + asset_content_type: application/gzip From 29339d59e3439b810b28a37bbf2054d8ce0f5ca2 Mon Sep 17 00:00:00 2001 From: cloudhan Date: Thu, 30 Mar 2023 00:19:02 +0800 Subject: [PATCH 07/43] Relax the _check_opts impl (#79) For example, options like "--compiler-options=...", which is equivalent to "-Xcompiler", however, will be disallowed due to a match with `opt.startswith("--compile")`. --- cuda/private/cuda_helper.bzl | 38 ++++++++++++++++++++++++------------ 1 file changed, 26 insertions(+), 12 deletions(-) diff --git a/cuda/private/cuda_helper.bzl b/cuda/private/cuda_helper.bzl index ea66c124..fb5a0cc0 100644 --- a/cuda/private/cuda_helper.bzl +++ b/cuda/private/cuda_helper.bzl @@ -120,22 +120,36 @@ def _resolve_includes(ctx, path): def _check_opts(opt): opt = opt.strip() + disallow_list_exact = [ + "--cuda", + "-cuda", + "--preprocess", + "-E", + "--compile", + "-c", + "--cubin", + "-cubin", + "--ptx", + "-ptx", + "--fatbin", + "-fatbin", + "--device-link", + "-dlink", + "--lib", + "-lib", + "--generate-dependencies", + "-M", + "--generate-nonsystem-dependencies", + "-MM", + "--run", + "-run", + ] if (opt.startswith("--generate-code") or opt.startswith("-gencode") or opt.startswith("--gpu-architecture") or opt.startswith("-arch") or opt.startswith("--gpu-code") or opt.startswith("-code") or opt.startswith("--relocatable-device-code") or opt.startswith("-rdc") or - opt.startswith("--cuda") or opt.startswith("-cuda") or - opt.startswith("--preprocess") or opt.startswith("-E") or - opt.startswith("--compile") or opt.startswith("-c") or - opt.startswith("--cubin") or opt.startswith("-cubin") or - opt.startswith("--ptx") or opt.startswith("-ptx") or - opt.startswith("--fatbin") or opt.startswith("-fatbin") or - opt.startswith("--device-link") or opt.startswith("-dlink") or - opt.startswith("--lib") or opt.startswith("-lib") or - opt.startswith("--generate-dependencies") or opt.startswith("-M") or - opt.startswith("--generate-nonsystem-dependencies") or opt.startswith("-MM") or - opt.startswith("--run") or opt.startswith("-run")): - fail(opt, "is not allowed to be specified directly via copts") + opt in disallow_list_exact): + fail(opt, "is not allowed to be specified directly via copts of rules_cuda related rules") return True def _get_cuda_archs_info(ctx): From 68a15a71366fd11dc49e7a2ee54edd9a87ad78a8 Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Fri, 31 Mar 2023 19:47:30 +0800 Subject: [PATCH 08/43] chore(deps): update dependency mkdocs-material to v9.1.5 (#82) --- docs/requirements.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/requirements.txt b/docs/requirements.txt index 73783653..0bc21092 100644 --- a/docs/requirements.txt +++ b/docs/requirements.txt @@ -1 +1 @@ -mkdocs-material==9.1.4 +mkdocs-material==9.1.5 From 21389bf36a841d812cb119995c847133e4285b14 Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Sat, 8 Apr 2023 09:35:06 +0800 Subject: [PATCH 09/43] chore(deps): update dependency mkdocs-material to v9.1.6 (#83) --- docs/requirements.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/requirements.txt b/docs/requirements.txt index 0bc21092..b94b4c28 100644 --- a/docs/requirements.txt +++ b/docs/requirements.txt @@ -1 +1 @@ -mkdocs-material==9.1.5 +mkdocs-material==9.1.6 From 537d49bbbf6d8947b1313800513f4e1172dbdb64 Mon Sep 17 00:00:00 2001 From: cloudhan Date: Wed, 12 Apr 2023 08:44:40 +0800 Subject: [PATCH 10/43] Allow //cuda:copts to be repeatable (#85) * Allow //cuda:copts to be repeatable * Also rename _default_host_copts as _default_cuda_copts --- cuda/BUILD.bazel | 7 +++---- cuda/private/cuda_helper.bzl | 2 +- cuda/private/rules/cuda_library.bzl | 2 +- cuda/private/rules/cuda_objects.bzl | 2 +- cuda/private/rules/flags.bzl | 13 +++++++++++++ 5 files changed, 19 insertions(+), 7 deletions(-) diff --git a/cuda/BUILD.bazel b/cuda/BUILD.bazel index fd89ecc9..2eba9a5c 100644 --- a/cuda/BUILD.bazel +++ b/cuda/BUILD.bazel @@ -3,9 +3,8 @@ load( "@bazel_skylib//rules:common_settings.bzl", "bool_flag", "string_flag", - "string_list_flag", ) -load("//cuda/private:rules/flags.bzl", "cuda_archs_flag") +load("//cuda/private:rules/flags.bzl", "cuda_archs_flag", "repeatable_string_flag") package(default_visibility = ["//visibility:public"]) @@ -67,9 +66,9 @@ config_setting( ) # Command line flag for copts to add to cuda_library() compile command. -string_list_flag( +repeatable_string_flag( name = "copts", - build_setting_default = [], + build_setting_default = "", ) # Command line flag to specify the CUDA runtime. Use this target as CUDA diff --git a/cuda/private/cuda_helper.bzl b/cuda/private/cuda_helper.bzl index fb5a0cc0..ab344736 100644 --- a/cuda/private/cuda_helper.bzl +++ b/cuda/private/cuda_helper.bzl @@ -253,7 +253,7 @@ def _create_common(ctx): # gather compile info defines = [] local_defines = [i for i in attr.local_defines] - compile_flags = attr._default_host_copts[BuildSettingInfo].value + [o for o in attr.copts if _check_opts(o)] + compile_flags = attr._default_cuda_copts[BuildSettingInfo].value + [o for o in attr.copts if _check_opts(o)] link_flags = [] if hasattr(attr, "linkopts"): link_flags.extend([o for o in attr.linkopts if _check_opts(o)]) diff --git a/cuda/private/rules/cuda_library.bzl b/cuda/private/rules/cuda_library.bzl index b9900ba8..bb723b4e 100644 --- a/cuda/private/rules/cuda_library.bzl +++ b/cuda/private/rules/cuda_library.bzl @@ -120,7 +120,7 @@ cuda_library = rule( "ptxasopts": attr.string_list(doc = "Add these flags to the ptxas command."), "_builtin_deps": attr.label_list(default = ["//cuda:runtime"]), "_cc_toolchain": attr.label(default = "@bazel_tools//tools/cpp:current_cc_toolchain"), # legacy behaviour - "_default_host_copts": attr.label(default = "//cuda:copts"), + "_default_cuda_copts": attr.label(default = "//cuda:copts"), "_default_cuda_archs": attr.label(default = "//cuda:archs"), }, fragments = ["cpp"], diff --git a/cuda/private/rules/cuda_objects.bzl b/cuda/private/rules/cuda_objects.bzl index bd8d2996..e0061f5b 100644 --- a/cuda/private/rules/cuda_objects.bzl +++ b/cuda/private/rules/cuda_objects.bzl @@ -93,7 +93,7 @@ code and device link time optimization source files.""", "local_defines": attr.string_list(doc = "List of defines to add to the compile line, but only apply to this rule."), "ptxasopts": attr.string_list(doc = "Add these flags to the ptxas command."), "_cc_toolchain": attr.label(default = "@bazel_tools//tools/cpp:current_cc_toolchain"), # legacy behaviour - "_default_host_copts": attr.label(default = "//cuda:copts"), + "_default_cuda_copts": attr.label(default = "//cuda:copts"), "_default_cuda_archs": attr.label(default = "//cuda:archs"), }, fragments = ["cpp"], diff --git a/cuda/private/rules/flags.bzl b/cuda/private/rules/flags.bzl index e96957ec..f76648fb 100644 --- a/cuda/private/rules/flags.bzl +++ b/cuda/private/rules/flags.bzl @@ -1,3 +1,4 @@ +load("@bazel_skylib//rules:common_settings.bzl", "BuildSettingInfo") load("//cuda/private:cuda_helper.bzl", "cuda_helper") load("//cuda/private:providers.bzl", "CudaArchsInfo") @@ -45,3 +46,15 @@ Best Practices: build_setting = config.string(flag = True), provides = [CudaArchsInfo], ) + +def _repeatable_string_flag_impl(ctx): + flags = ctx.build_setting_value + if(flags == [""]): + flags = [] + return BuildSettingInfo(value = flags) + +repeatable_string_flag = rule( + implementation = _repeatable_string_flag_impl, + build_setting = config.string(flag = True, allow_multiple = True), + provides = [BuildSettingInfo], +) From 61b13b026292ee6b245f017963a7d80341c0be8c Mon Sep 17 00:00:00 2001 From: cloudhan Date: Wed, 12 Apr 2023 09:10:01 +0800 Subject: [PATCH 11/43] Fix local docs build hint (#87) Fix local build hint --- docs/build-docs.sh | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/build-docs.sh b/docs/build-docs.sh index 37e2a7cb..ef095ee5 100755 --- a/docs/build-docs.sh +++ b/docs/build-docs.sh @@ -21,7 +21,7 @@ function compose-versioned-site { python versioning.py generated/ --force printf "\nRun following command to update version list then serve locally:\n\n" - printf "\tpython -m http.server -d generate/\n\n" + printf "\tpython -m http.server -d generated/\n\n" } From c0f34ce9dbc566b4c535bfc4cb93b4088f96bb80 Mon Sep 17 00:00:00 2001 From: James Sharpe Date: Wed, 12 Apr 2023 06:03:12 +0100 Subject: [PATCH 12/43] Allow multiple 'local' installs of cuda to be specified (#66) --- .github/workflows/build-tests.yaml | 8 ++++---- MODULE.bazel | 6 +++--- WORKSPACE.bzlmod | 4 ---- cuda/extensions.bzl | 25 +++++++++++++++++++++++-- cuda/private/repositories.bzl | 19 +++++++++++-------- cuda/repositories.bzl | 3 ++- examples/MODULE.bazel | 10 ++++++---- 7 files changed, 49 insertions(+), 26 deletions(-) delete mode 100644 WORKSPACE.bzlmod diff --git a/.github/workflows/build-tests.yaml b/.github/workflows/build-tests.yaml index 2e39d581..ac75c639 100644 --- a/.github/workflows/build-tests.yaml +++ b/.github/workflows/build-tests.yaml @@ -75,9 +75,9 @@ jobs: - run: bazelisk build @rules_cuda_examples//if_cuda:main - run: bazelisk build @rules_cuda_examples//if_cuda:main --enable_cuda=False - - run: bazelisk build @rules_cuda_examples//basic:main --config=bzlmod - - run: bazelisk build @rules_cuda_examples//rdc:main --config=bzlmod - - run: bazelisk build @rules_cuda_examples//if_cuda:main --config=bzlmod - - run: bazelisk build @rules_cuda_examples//if_cuda:main --enable_cuda=False --config=bzlmod + - run: cd examples && bazelisk build //basic:main --config=bzlmod + - run: cd examples && bazelisk build //rdc:main --config=bzlmod + - run: cd examples && bazelisk build //if_cuda:main --config=bzlmod + - run: cd examples && bazelisk build //if_cuda:main --enable_cuda=False --config=bzlmod - run: bazelisk shutdown diff --git a/MODULE.bazel b/MODULE.bazel index eae6e6fb..8de8f6b0 100644 --- a/MODULE.bazel +++ b/MODULE.bazel @@ -1,13 +1,13 @@ module( name = "rules_cuda", compatibility_level = 1, - version = "0.1.1", + version = "0.0.0", ) bazel_dep(name = "bazel_skylib", version = "1.2.1") -bazel_dep(name = "platforms", version = "0.0.4") +bazel_dep(name = "platforms", version = "0.0.6") -toolchain = use_extension("@rules_cuda//cuda:extensions.bzl", "local_toolchain") +toolchain = use_extension("@rules_cuda//cuda:extensions.bzl", "toolchain") use_repo(toolchain, "local_cuda") register_toolchains( diff --git a/WORKSPACE.bzlmod b/WORKSPACE.bzlmod deleted file mode 100644 index a277358a..00000000 --- a/WORKSPACE.bzlmod +++ /dev/null @@ -1,4 +0,0 @@ -local_repository( - name = "rules_cuda_examples", - path = "examples", -) diff --git a/cuda/extensions.bzl b/cuda/extensions.bzl index 649662e5..b6014dd8 100644 --- a/cuda/extensions.bzl +++ b/cuda/extensions.bzl @@ -2,7 +2,28 @@ load("//cuda/private:repositories.bzl", "local_cuda") +cuda_toolkit = tag_class(attrs = { + "name": attr.string(doc = "Name for the toolchain repository", default = "local_cuda"), + "toolkit_path": attr.string(doc = "Path to the CUDA SDK, if empty the environment variable CUDA_PATH will be used to deduce this path."), +}) + def _init(module_ctx): - local_cuda(name = "local_cuda") + registrations = {} + for mod in module_ctx.modules: + for toolchain in mod.tags.local_toolchain: + if not mod.is_root: + fail("Only the root module may override the path for the local cuda toolchain") + if toolchain.name in registrations.keys(): + if toolchain.toolkit_path == registrations[toolchain.name]: + # No problem to register a matching toolchain twice + continue + fail("Multiple conflicting toolchains declared for name {} ({} and {}".format(toolchain.name, toolchain.toolkit_path, registrations[toolchain.name])) + else: + registrations[toolchain.name] = toolchain.toolkit_path + for name, toolkit_path in registrations.items(): + local_cuda(name = name, toolkit_path = toolkit_path) -local_toolchain = module_extension(implementation = _init) +toolchain = module_extension( + implementation = _init, + tag_classes = {"local_toolchain": cuda_toolkit}, +) diff --git a/cuda/private/repositories.bzl b/cuda/private/repositories.bzl index d420eddc..9a29f4c7 100644 --- a/cuda/private/repositories.bzl +++ b/cuda/private/repositories.bzl @@ -29,10 +29,10 @@ def detect_cuda_toolkit(repository_ctx): """Detect CUDA Toolkit. The path to CUDA Toolkit is determined as: - + - the value of `toolkit_path` passed to local_cuda as an attribute - taken from `CUDA_PATH` environment variable or - - determined through `which ptxas` or - - defaults to `/usr/local/cuda` + - determined through 'which ptxas' or + - defaults to '/usr/local/cuda' Args: repository_ctx: repository_ctx @@ -40,7 +40,9 @@ def detect_cuda_toolkit(repository_ctx): Returns: A struct contains the information of CUDA Toolkit. """ - cuda_path = repository_ctx.os.environ.get("CUDA_PATH", None) + cuda_path = repository_ctx.attr.toolkit_path + if cuda_path == "": + cuda_path = repository_ctx.os.environ.get("CUDA_PATH", None) if cuda_path == None: ptxas_path = repository_ctx.which("ptxas") if ptxas_path: @@ -65,13 +67,13 @@ def detect_cuda_toolkit(repository_ctx): fatbinary = "@rules_cuda//cuda/dummy:fatbinary" if cuda_path != None: if repository_ctx.path(cuda_path + "/bin/nvlink" + bin_ext).exists: - nvlink = "@local_cuda//:cuda/bin/nvlink" + bin_ext + nvlink = ":cuda/bin/nvlink{}".format(bin_ext) if repository_ctx.path(cuda_path + "/bin/crt/link.stub").exists: - link_stub = "@local_cuda//:cuda/bin/crt/link.stub" + link_stub = ":cuda/bin/crt/link.stub" if repository_ctx.path(cuda_path + "/bin/bin2c" + bin_ext).exists: - bin2c = "@local_cuda//:cuda/bin/bin2c" + bin_ext + bin2c = ":cuda/bin/bin2c{}".format(bin_ext) if repository_ctx.path(cuda_path + "/bin/fatbinary" + bin_ext).exists: - fatbinary = "@local_cuda//:cuda/bin/fatbinary" + bin_ext + fatbinary = ":cuda/bin/fatbinary{}".format(bin_ext) nvcc_version_major = -1 nvcc_version_minor = -1 @@ -197,6 +199,7 @@ def _local_cuda_impl(repository_ctx): local_cuda = repository_rule( implementation = _local_cuda_impl, + attrs = {"toolkit_path": attr.string(mandatory = False)}, configure = True, local = True, environ = ["CUDA_PATH", "PATH", "CUDA_CLANG_PATH", "BAZEL_LLVM"], diff --git a/cuda/repositories.bzl b/cuda/repositories.bzl index 73591d47..5ee24d69 100644 --- a/cuda/repositories.bzl +++ b/cuda/repositories.bzl @@ -1,5 +1,6 @@ -load("//cuda/private:repositories.bzl", _rules_cuda_dependencies = "rules_cuda_dependencies") +load("//cuda/private:repositories.bzl", _local_cuda = "local_cuda", _rules_cuda_dependencies = "rules_cuda_dependencies") load("//cuda/private:toolchain.bzl", _register_detected_cuda_toolchains = "register_detected_cuda_toolchains") rules_cuda_dependencies = _rules_cuda_dependencies +local_cuda = _local_cuda register_detected_cuda_toolchains = _register_detected_cuda_toolchains diff --git a/examples/MODULE.bazel b/examples/MODULE.bazel index eda468f1..76a87773 100644 --- a/examples/MODULE.bazel +++ b/examples/MODULE.bazel @@ -4,9 +4,11 @@ module( version = "0.0.0", ) -bazel_dep(name = "rules_cuda", version = "0.1.1") +bazel_dep(name = "rules_cuda", version = "0.1.3") +local_path_override(module_name = "rules_cuda", path = "..") -cuda_toolchain = use_extension("@rules_cuda//cuda:extensions.bzl", "local_toolchain") -use_repo(cuda_toolchain, "local_cuda") +cuda = use_extension("@rules_cuda//cuda:extensions.bzl", "toolchain") -local_path_override(module_name = "rules_cuda", path = "..") +cuda.local_toolchain(name = "local_cuda", toolkit_path = "") + +use_repo(cuda, "local_cuda") From 36202306c713a40506204eb381704ed43bcd563d Mon Sep 17 00:00:00 2001 From: cloudhan Date: Wed, 12 Apr 2023 20:15:41 +0800 Subject: [PATCH 13/43] Fix possibly conflict artifact names (#81) Say, build with `srcs = ["kernel.cu", "nested/kernel.cu"]` will result: ``` MandatoryInputs: Attempted action contains artifacts not in previous action (first 5): basic/nested/kernel.cu Previous action contains artifacts not in attempted action (first 5): basic/kernel.cu Outputs: are equal ERROR: /home/cloud/rules_cuda/examples/basic/BUILD.bazel:5:13: for basic/_objs/kernel/kernel.o, previous action: action 'Compiling basic/kernel.cu', attempted action: action 'Compiling basic/nested/kernel.cu' ``` We use basename indices to deduplicate as in cc rules. --- cuda/private/actions/compile.bzl | 20 ++++++++++++++++++-- cuda/private/rules/cuda_library.bzl | 17 +++++++---------- cuda/private/rules/cuda_objects.bzl | 24 ++++++++---------------- 3 files changed, 33 insertions(+), 28 deletions(-) diff --git a/cuda/private/actions/compile.bzl b/cuda/private/actions/compile.bzl index 4f24ee1c..44f3ed76 100644 --- a/cuda/private/actions/compile.bzl +++ b/cuda/private/actions/compile.bzl @@ -13,7 +13,10 @@ def compile( """Perform CUDA compilation, return compiled object files. Notes: - If `rdc` is set to `True`, then an additional step of device link must be performed. + + - If `rdc` is set to `True`, then an additional step of device link must be performed. + - The rules should call this action only once in case srcs have non-unique basenames, + say `foo/kernel.cu` and `bar/kernel.cu`. Args: ctx: A [context object](https://bazel.build/rules/lib/ctx). @@ -34,14 +37,27 @@ def compile( cuda_feature_config = cuda_helper.configure_features(ctx, cuda_toolchain, requested_features = [ACTION_NAMES.cuda_compile]) artifact_category_name = cuda_helper.get_artifact_category_from_action(ACTION_NAMES.cuda_compile, pic, rdc) - ret = [] + basename_counter = {} + src_and_indexed_basenames = [] for src in srcs: # this also filter out all header files basename = cuda_helper.get_basename_without_ext(src.basename, ALLOW_CUDA_SRCS, fail_if_not_match = False) if not basename: continue + basename_index = basename_counter.setdefault(basename, default=0) + basename_counter[basename] += 1 + src_and_indexed_basenames.append((src, basename, basename_index)) + ret = [] + for src, basename, basename_index in src_and_indexed_basenames: + filename = None filename = cuda_helper.get_artifact_name(cuda_toolchain, artifact_category_name, basename) + # Objects are placed in _objs//. + # For files with the same basename, say srcs = ["kernel.cu", "foo/kernel.cu", "bar/kernel.cu"], we get + # _objs//0/kernel., _objs//1/kernel., _objs//2/kernel.. + # Otherwise, the index is not presented. + if basename_counter[basename] > 1: + filename = "{}/{}".format(basename_index, filename) obj_file = actions.declare_file("_objs/{}/{}".format(ctx.attr.name, filename)) ret.append(obj_file) diff --git a/cuda/private/rules/cuda_library.bzl b/cuda/private/rules/cuda_library.bzl index bb723b4e..75c2360c 100644 --- a/cuda/private/rules/cuda_library.bzl +++ b/cuda/private/rules/cuda_library.bzl @@ -23,17 +23,14 @@ def _cuda_library_impl(ctx): if not use_rdc: use_rdc = cuda_helper.check_must_enforce_rdc(cuda_archs_info = common.cuda_archs_info) - # outputs - objects = [] - pic_objects = [] - - for src in attr.srcs: - files = src[DefaultInfo].files.to_list() - objects.extend(compile(ctx, cuda_toolchain, cc_toolchain, files, common, pic = False, rdc = use_rdc)) - pic_objects.extend(compile(ctx, cuda_toolchain, cc_toolchain, files, common, pic = True, rdc = use_rdc)) + # flatten first, so that non-unique basenames can be properly deduplicated + src_files = [] + for src in ctx.attr.srcs: + src_files.extend(src[DefaultInfo].files.to_list()) - objects = depset(objects) - pic_objects = depset(pic_objects) + # outputs + objects = depset(compile(ctx, cuda_toolchain, cc_toolchain, src_files, common, pic = False, rdc = use_rdc)) + pic_objects = depset(compile(ctx, cuda_toolchain, cc_toolchain, src_files, common, pic = True, rdc = use_rdc)) # if rdc is enabled for this cuda_library, then we need futher do a pass of device link if use_rdc: diff --git a/cuda/private/rules/cuda_objects.bzl b/cuda/private/rules/cuda_objects.bzl index e0061f5b..b0fccdc3 100644 --- a/cuda/private/rules/cuda_objects.bzl +++ b/cuda/private/rules/cuda_objects.bzl @@ -14,24 +14,16 @@ def _cuda_objects_impl(ctx): common = cuda_helper.create_common(ctx) - # outputs - objects = [] - rdc_objects = [] - pic_objects = [] - rdc_pic_objects = [] - + # flatten first, so that non-unique basenames can be properly deduplicated + src_files = [] for src in ctx.attr.srcs: - files = src[DefaultInfo].files.to_list() + src_files.extend(src[DefaultInfo].files.to_list()) - objects.extend(compile(ctx, cuda_toolchain, cc_toolchain, files, common, pic = False, rdc = False)) - pic_objects.extend(compile(ctx, cuda_toolchain, cc_toolchain, files, common, pic = True, rdc = False)) - rdc_objects.extend(compile(ctx, cuda_toolchain, cc_toolchain, files, common, pic = False, rdc = True)) - rdc_pic_objects.extend(compile(ctx, cuda_toolchain, cc_toolchain, files, common, pic = True, rdc = True)) - - objects = depset(objects) - pic_objects = depset(pic_objects) - rdc_objects = depset(rdc_objects) - rdc_pic_objects = depset(rdc_pic_objects) + # outputs + objects = depset(compile(ctx, cuda_toolchain, cc_toolchain, src_files, common, pic = False, rdc = False)) + rdc_objects = depset(compile(ctx, cuda_toolchain, cc_toolchain, src_files, common, pic = False, rdc = True)) + pic_objects = depset(compile(ctx, cuda_toolchain, cc_toolchain, src_files, common, pic = True, rdc = False)) + rdc_pic_objects = depset(compile(ctx, cuda_toolchain, cc_toolchain, src_files, common, pic = True, rdc = True)) compilation_ctx = cc_common.create_compilation_context( headers = common.headers, From c8b9fb2ba60cc6fc5be576c287888421d212436f Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Wed, 19 Apr 2023 07:27:54 +0800 Subject: [PATCH 14/43] chore(deps): update dependency bazel to v6.1.2 (#89) --- .bazelversion | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.bazelversion b/.bazelversion index f3b5af39..5e325424 100644 --- a/.bazelversion +++ b/.bazelversion @@ -1 +1 @@ -6.1.1 +6.1.2 From 251475dd82929e9e23cad4a2d502a7aefb767c29 Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Sat, 22 Apr 2023 13:48:13 +0100 Subject: [PATCH 15/43] chore(deps): update dependency mkdocs-material to v9.1.7 (#90) --- docs/requirements.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/requirements.txt b/docs/requirements.txt index b94b4c28..97e59010 100644 --- a/docs/requirements.txt +++ b/docs/requirements.txt @@ -1 +1 @@ -mkdocs-material==9.1.6 +mkdocs-material==9.1.7 From 1e9954093c7d789c628ddf052035f725249c122f Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Tue, 25 Apr 2023 07:07:36 +0100 Subject: [PATCH 16/43] chore(deps): update dependency mkdocs-material to v9.1.8 (#91) --- docs/requirements.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/requirements.txt b/docs/requirements.txt index 97e59010..e64364b9 100644 --- a/docs/requirements.txt +++ b/docs/requirements.txt @@ -1 +1 @@ -mkdocs-material==9.1.7 +mkdocs-material==9.1.8 From 5633f0c0f72934fa2f68bb2f217f3bc32ab88f9b Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Tue, 2 May 2023 19:05:21 +0800 Subject: [PATCH 17/43] chore(deps): update dependency mkdocs-material to v9.1.9 (#92) --- docs/requirements.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/requirements.txt b/docs/requirements.txt index e64364b9..614ba112 100644 --- a/docs/requirements.txt +++ b/docs/requirements.txt @@ -1 +1 @@ -mkdocs-material==9.1.8 +mkdocs-material==9.1.9 From eb46b27c85805a5dcd2e42a6fcd6f4276f61551c Mon Sep 17 00:00:00 2001 From: cloudhan Date: Wed, 3 May 2023 17:01:20 +0800 Subject: [PATCH 18/43] Overhaul the URLs to the update new repo (#93) --- .bazelrc | 2 +- README.md | 8 ++++---- examples/.bazelrc | 2 +- 3 files changed, 6 insertions(+), 6 deletions(-) diff --git a/.bazelrc b/.bazelrc index 6362e03c..474360a0 100644 --- a/.bazelrc +++ b/.bazelrc @@ -11,7 +11,7 @@ build --enable_cuda=True build:clang --repo_env=CC=clang build:clang --//cuda:compiler=clang -# https://github.com/cloudhan/rules_cuda/issues/1 +# https://github.com/bazel-contrib/rules_cuda/issues/1 build --ui_event_filters=-INFO common:bzlmod --enable_bzlmod diff --git a/README.md b/README.md index 74c389b8..be758cba 100644 --- a/README.md +++ b/README.md @@ -25,8 +25,8 @@ register_detected_cuda_toolchains() ensure the host compiler is available. On windows, this means that you will also need to set the environment variable `BAZEL_VC` properly. -[`detect_cuda_toolkit`](https://github.com/cloudhan/rules_cuda/blob/f534446357/cuda/private/repositories.bzl#L44-L57) -and [`detect_clang`](https://github.com/cloudhan/rules_cuda/blob/f534446357/cuda/private/repositories.bzl#L129-L143) +[`detect_cuda_toolkit`](https://github.com/bazel-contrib/rules_cuda/blob/5633f0c0f7/cuda/private/repositories.bzl#L28-L58) +and [`detect_clang`](https://github.com/bazel-contrib/rules_cuda/blob/5633f0c0f7/cuda/private/repositories.bzl#L143-L166) determains how the toolchains are detected. ### Rules @@ -67,7 +67,7 @@ bazel build --cuda_archs=compute_61:compute_61,sm_61 - `@rules_cuda//cuda:archs` - Select the cuda archs to support. See [cuda_archs specification DSL grammar](https://github.com/cloudhan/rules_cuda/blob/f534446357/cuda/private/providers.bzl#L43-L65). + Select the cuda archs to support. See [cuda_archs specification DSL grammar](https://github.com/bazel-contrib/rules_cuda/blob/5633f0c0f7/cuda/private/rules/flags.bzl#L14-L44). - `@rules_cuda//cuda:compiler` @@ -87,7 +87,7 @@ Checkout the examples to see if it fits your needs. See [examples](./examples) for basic usage. -See [cloudhan/rules_cuda_examples](https://github.com/cloudhan/rules_cuda_examples) for extended real world projects. +See [rules_cuda_examples](https://github.com/cloudhan/rules_cuda_examples) for extended real world projects. ## Known issue diff --git a/examples/.bazelrc b/examples/.bazelrc index 6d5c25fa..c21ebf18 100644 --- a/examples/.bazelrc +++ b/examples/.bazelrc @@ -11,7 +11,7 @@ build --enable_cuda=True build:clang --repo_env=CC=clang build:clang --//cuda:compiler=clang -# https://github.com/cloudhan/rules_cuda/issues/1 +# https://github.com/bazel-contrib/rules_cuda/issues/1 build --ui_event_filters=-INFO common:bzlmod --enable_bzlmod From 915cdeb196e81172c141d1dd684281e95c68d84a Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Tue, 9 May 2023 09:41:48 +0800 Subject: [PATCH 19/43] chore(deps): update dependency mkdocs-material to v9.1.11 (#94) --- docs/requirements.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/requirements.txt b/docs/requirements.txt index 614ba112..978d3f20 100644 --- a/docs/requirements.txt +++ b/docs/requirements.txt @@ -1 +1 @@ -mkdocs-material==9.1.9 +mkdocs-material==9.1.11 From 68cd2eeb5003affbdbf2bffcacde3c4b87272a03 Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Wed, 10 May 2023 07:43:44 +0800 Subject: [PATCH 20/43] chore(deps): update dependency bazel to v6.2.0 (#95) --- .bazelversion | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.bazelversion b/.bazelversion index 5e325424..6abaeb2f 100644 --- a/.bazelversion +++ b/.bazelversion @@ -1 +1 @@ -6.1.2 +6.2.0 From d4d6b7b51dad5bf717d8e5bafe2ad94526308191 Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Fri, 12 May 2023 16:16:14 +0100 Subject: [PATCH 21/43] chore(deps): update dependency mkdocs-material to v9.1.12 (#96) Co-authored-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> --- docs/requirements.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/requirements.txt b/docs/requirements.txt index 978d3f20..c6d8bc3d 100644 --- a/docs/requirements.txt +++ b/docs/requirements.txt @@ -1 +1 @@ -mkdocs-material==9.1.11 +mkdocs-material==9.1.12 From 39bcae997adeb2cb90a813ed068c4d533224cfb0 Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Tue, 16 May 2023 23:18:45 +0100 Subject: [PATCH 22/43] chore(deps): update dependency io_bazel_stardoc to v0.5.4 (#98) Co-authored-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> --- docs/WORKSPACE.bazel | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/docs/WORKSPACE.bazel b/docs/WORKSPACE.bazel index 806a7b96..77432552 100644 --- a/docs/WORKSPACE.bazel +++ b/docs/WORKSPACE.bazel @@ -13,10 +13,10 @@ load("@bazel_tools//tools/build_defs/repo:http.bzl", "http_archive") http_archive( name = "io_bazel_stardoc", - sha256 = "3fd8fec4ddec3c670bd810904e2e33170bedfe12f90adf943508184be458c8bb", + sha256 = "ec57139e466faae563f2fc39609da4948a479bb51b6d67aedd7d9b1b8059c433", urls = [ - "https://mirror.bazel.build/github.com/bazelbuild/stardoc/releases/download/0.5.3/stardoc-0.5.3.tar.gz", - "https://github.com/bazelbuild/stardoc/releases/download/0.5.3/stardoc-0.5.3.tar.gz", + "https://mirror.bazel.build/github.com/bazelbuild/stardoc/releases/download/0.5.4/stardoc-0.5.4.tar.gz", + "https://github.com/bazelbuild/stardoc/releases/download/0.5.4/stardoc-0.5.4.tar.gz", ], ) From 6d878bf1a5e440ea31f53c9944fa77a17f333e06 Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Tue, 16 May 2023 23:19:09 +0100 Subject: [PATCH 23/43] chore(deps): update dependency mkdocs-material to v9.1.13 (#97) Co-authored-by: renovate[bot] <29139614+renovate[bot]@users.noreply.github.com> --- docs/requirements.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/requirements.txt b/docs/requirements.txt index c6d8bc3d..e4b45926 100644 --- a/docs/requirements.txt +++ b/docs/requirements.txt @@ -1 +1 @@ -mkdocs-material==9.1.12 +mkdocs-material==9.1.13 From f1219b104ef81f61ec8695fda8dc0035d37a896d Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Sat, 20 May 2023 22:48:35 +0800 Subject: [PATCH 24/43] chore(deps): update dependency mkdocs-material to v9.1.14 (#100) --- docs/requirements.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/requirements.txt b/docs/requirements.txt index e4b45926..9c88e3cf 100644 --- a/docs/requirements.txt +++ b/docs/requirements.txt @@ -1 +1 @@ -mkdocs-material==9.1.13 +mkdocs-material==9.1.14 From f5cb8b1961668db5fc8f4ea160e69d2181e7f622 Mon Sep 17 00:00:00 2001 From: cloudhan Date: Mon, 22 May 2023 16:32:39 +0800 Subject: [PATCH 25/43] Slow the renovate bot down (#101) --- renovate.json | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/renovate.json b/renovate.json index 4bd832f5..66f08137 100644 --- a/renovate.json +++ b/renovate.json @@ -1,4 +1,5 @@ { "$schema": "https://docs.renovatebot.com/renovate-schema.json", - "extends": ["config:base"] + "extends": ["config:base"], + "schedule": ["on the first day of the month"] } From 962fdd9283aaf8a0fb6764100467813809789701 Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Thu, 1 Jun 2023 09:59:50 +0800 Subject: [PATCH 26/43] chore(deps): update dependency mkdocs-material to v9.1.15 (#104) --- docs/requirements.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/requirements.txt b/docs/requirements.txt index 9c88e3cf..71599d29 100644 --- a/docs/requirements.txt +++ b/docs/requirements.txt @@ -1 +1 @@ -mkdocs-material==9.1.14 +mkdocs-material==9.1.15 From 00a1c59013464bcb3f643a4751b3859428c29659 Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Thu, 1 Jun 2023 10:01:05 +0800 Subject: [PATCH 27/43] chore(deps): update dependency io_bazel_stardoc to v0.5.6 (#103) --- docs/WORKSPACE.bazel | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) diff --git a/docs/WORKSPACE.bazel b/docs/WORKSPACE.bazel index 77432552..5039acd3 100644 --- a/docs/WORKSPACE.bazel +++ b/docs/WORKSPACE.bazel @@ -13,10 +13,10 @@ load("@bazel_tools//tools/build_defs/repo:http.bzl", "http_archive") http_archive( name = "io_bazel_stardoc", - sha256 = "ec57139e466faae563f2fc39609da4948a479bb51b6d67aedd7d9b1b8059c433", + sha256 = "dfbc364aaec143df5e6c52faf1f1166775a5b4408243f445f44b661cfdc3134f", urls = [ - "https://mirror.bazel.build/github.com/bazelbuild/stardoc/releases/download/0.5.4/stardoc-0.5.4.tar.gz", - "https://github.com/bazelbuild/stardoc/releases/download/0.5.4/stardoc-0.5.4.tar.gz", + "https://mirror.bazel.build/github.com/bazelbuild/stardoc/releases/download/0.5.6/stardoc-0.5.6.tar.gz", + "https://github.com/bazelbuild/stardoc/releases/download/0.5.6/stardoc-0.5.6.tar.gz", ], ) From 24e5d37bbd6f962981ff29a80715917526d8201e Mon Sep 17 00:00:00 2001 From: Laurenz Date: Fri, 2 Jun 2023 20:10:08 +0200 Subject: [PATCH 28/43] Add NPP (#106) * Add NPP See https://docs.nvidia.com/cuda/npp/index.html --- cuda/runtime/BUILD.local_cuda | 64 +++++++++++++++++++++++++++++++++++ 1 file changed, 64 insertions(+) diff --git a/cuda/runtime/BUILD.local_cuda b/cuda/runtime/BUILD.local_cuda index 88ca2e26..a775673f 100644 --- a/cuda/runtime/BUILD.local_cuda +++ b/cuda/runtime/BUILD.local_cuda @@ -473,3 +473,67 @@ cc_library( ":nvtx_lib", ]), ) + +# NPP +_NPP_LIBS = { + "nppc": [ + "npp.h", + "nppcore.h", + "nppdefs.h", + ], + "nppial": ["nppi_arithmetic_and_logical_operations.h"], + "nppicc": ["nppi_color_conversion.h"], + "nppidei": ["nppi_data_exchange_and_initialization.h"], + "nppif": ["nppi_filtering_functions.h"], + "nppig": ["nppi_geometry_transforms.h"], + "nppim": ["nppi_morphological_operations.h"], + "nppist": [ + "nppi_statistics_functions.h", + "nppi_linear_transforms.h", + ], + "nppisu": ["nppi_support_functions.h"], + "nppitc": ["nppi_threshold_and_compare_operations.h"], + "npps": [ + "npps_arithmetic_and_logical_operations.h", + "npps_conversion_functions.h", + "npps_filtering_functions.h", + "npps.h", + "npps_initialization.h", + "npps_statistics_functions.h", + "npps_support_functions.h", + ], +} + +[ + cc_import( + name = name + "_so", + shared_library = "cuda/lib64/lib{}.so".format(name), + target_compatible_with = ["@platforms//os:linux"], + ) + for name in _NPP_LIBS.keys() +] + +[ + cc_import( + name = name + "_lib", + interface_library = "cuda/lib/x64/{}.lib".format(name), + system_provided = 1, + target_compatible_with = ["@platforms//os:windows"], + ) + for name in _NPP_LIBS.keys() +] + +[ + cc_library( + name = name, + hdrs = ["cuda/include/" + hdr for hdr in hdrs], + includes = ["cuda/include"], + visibility = ["//visibility:public"], + deps = ([":nppc"] if name != "nppc" else []) + if_linux([ + ":{}_so".format(name), + ]) + if_windows([ + ":{}_lib".format(name), + ]), + ) + for name, hdrs in _NPP_LIBS.items() +] From 74df4f81af8d8389645422fd01835a0912341b40 Mon Sep 17 00:00:00 2001 From: cloudhan Date: Fri, 23 Jun 2023 12:27:24 +0800 Subject: [PATCH 29/43] Use windows-2019 for utilities tests (#112) Use windows-2019 os for utilities tests bazel 5.x somehow cannot recognize VS 2022 which is bundled in windows-latest. --- .github/workflows/utilities-tests.yaml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/utilities-tests.yaml b/.github/workflows/utilities-tests.yaml index 51720473..ec6df549 100644 --- a/.github/workflows/utilities-tests.yaml +++ b/.github/workflows/utilities-tests.yaml @@ -15,7 +15,7 @@ jobs: matrix: os: - ubuntu-20.04 - - windows-latest + - windows-2019 bazel-version: - 5.0.0 - 5.2.0 From 59d50982c0c0a462746f64ae574d24f81fdeed7b Mon Sep 17 00:00:00 2001 From: Gary Miguel Date: Thu, 22 Jun 2023 21:30:33 -0700 Subject: [PATCH 30/43] add cuda_device_debug feature (#108) --- README.md | 6 ++++++ cuda/private/toolchain_configs/nvcc.bzl | 13 +++++++++++++ cuda/private/toolchain_configs/nvcc_msvc.bzl | 19 ++++++++++++++++++- 3 files changed, 37 insertions(+), 1 deletion(-) diff --git a/README.md b/README.md index be758cba..7d6d3c2c 100644 --- a/README.md +++ b/README.md @@ -81,6 +81,12 @@ bazel build --cuda_archs=compute_61:compute_61,sm_61 Set the default cudart to link, for example, `--@rules_cuda//cuda:runtime=@local_cuda//:cuda_runtime_static` link the static cuda runtime. +- `--features=cuda_device_debug` + + Sets nvcc flags to enable debug information in device code. + Currently ignored for clang, where `--compilation_mode=debug` applies to both + host and device code. + ## Examples Checkout the examples to see if it fits your needs. diff --git a/cuda/private/toolchain_configs/nvcc.bzl b/cuda/private/toolchain_configs/nvcc.bzl index 72e5fe8b..66cba5cf 100644 --- a/cuda/private/toolchain_configs/nvcc.bzl +++ b/cuda/private/toolchain_configs/nvcc.bzl @@ -310,6 +310,8 @@ def _impl(ctx): flag_set( actions = [ACTION_NAMES.cuda_compile], flag_groups = [flag_group(flags = [ + "--dopt", # the default depends on the value of --device-debug (-G), so set it explicitly. + "on", "-Xcompiler", "-g0", "-O2", @@ -419,6 +421,16 @@ def _impl(ctx): ], ) + cuda_device_debug_feature = feature( + name = "cuda_device_debug", + flag_sets = [ + flag_set( + actions = [ACTION_NAMES.cuda_compile], + flag_groups = [flag_group(flags = ["--device-debug"])], + ), + ], + ) + action_configs = [ cuda_compile_action, cuda_device_link_action, @@ -445,6 +457,7 @@ def _impl(ctx): nvcc_allow_unsupported_compiler_feature, nvcc_relaxed_constexpr_feature, nvcc_extended_lambda_feature, + cuda_device_debug_feature, ] return [CudaToolchainConfigInfo( diff --git a/cuda/private/toolchain_configs/nvcc_msvc.bzl b/cuda/private/toolchain_configs/nvcc_msvc.bzl index 65c16a0e..1fbd38c6 100644 --- a/cuda/private/toolchain_configs/nvcc_msvc.bzl +++ b/cuda/private/toolchain_configs/nvcc_msvc.bzl @@ -355,7 +355,13 @@ def _impl(ctx): flag_sets = [ flag_set( actions = [ACTION_NAMES.cuda_compile], - flag_groups = [flag_group(flags = ["-DNDEBUG", "-Xcompiler", "/O2"])], + flag_groups = [flag_group(flags = [ + "--dopt", # the default depends on the value of --device-debug (-G), so set it explicitly. + "on", + "-DNDEBUG", + "-Xcompiler", + "/O2", + ])], ), ], implies = ["frame_pointer"], @@ -499,6 +505,16 @@ def _impl(ctx): ], ) + cuda_device_debug_feature = feature( + name = "cuda_device_debug", + flag_sets = [ + flag_set( + actions = [ACTION_NAMES.cuda_compile], + flag_groups = [flag_group(flags = ["--device-debug"])], + ), + ], + ) + action_configs = [ cuda_compile_action, cuda_device_link_action, @@ -531,6 +547,7 @@ def _impl(ctx): nvcc_allow_unsupported_compiler_feature, nvcc_extended_lambda_feature, nvcc_relaxed_constexpr_feature, + cuda_device_debug_feature, ] return [CudaToolchainConfigInfo( From 18eba6d463db35253788a94fdaa45e9863ab19f0 Mon Sep 17 00:00:00 2001 From: cloudhan Date: Fri, 23 Jun 2023 18:59:54 +0800 Subject: [PATCH 31/43] Add support for missing archs (#110) Add support for 89 and 90a --- cuda/private/cuda_helper.bzl | 34 +++++++++++++++++++++-------- cuda/private/providers.bzl | 2 ++ tests/flag/BUILD.bazel | 21 ++++++++++++++++++ tests/flag/flag_validation_test.bzl | 4 ++++ 4 files changed, 52 insertions(+), 9 deletions(-) diff --git a/cuda/private/cuda_helper.bzl b/cuda/private/cuda_helper.bzl index ab344736..f6d8a382 100644 --- a/cuda/private/cuda_helper.bzl +++ b/cuda/private/cuda_helper.bzl @@ -1,6 +1,7 @@ """private helpers""" load("@bazel_skylib//lib:paths.bzl", "paths") +load("@bazel_skylib//lib:types.bzl", "types") load("@bazel_skylib//rules:common_settings.bzl", "BuildSettingInfo") load("//cuda/private:action_names.bzl", "ACTION_NAMES") load("//cuda/private:artifact_categories.bzl", "ARTIFACT_CATEGORIES") @@ -8,22 +9,37 @@ load("//cuda/private:providers.bzl", "ArchSpecInfo", "CudaArchsInfo", "CudaInfo" load("//cuda/private:rules/common.bzl", "ALLOW_CUDA_HDRS") load("//cuda/private:toolchain_config_lib.bzl", "config_helper", "unique") +def _create_arch_number(arch_num_str): + """Create a structured architecture number. + + It is encoded as a tuple (int, suffix_str) to ease the comparison.""" + if types.is_int(arch_num_str): + return (int(arch_num_str), "") + else: + for i, c in enumerate(arch_num_str.elems()): + if not c.isdigit(): + break + return (int(arch_num_str[:i]), arch_num_str[i:]) + +def _format_arch_number(arch_num): + return str(arch_num[0]) + arch_num[1] + def _get_arch_number(arch_str): arch_str = arch_str.strip() - arch_num = None + arch_num_str = None if arch_str.startswith("compute_"): - arch_num = arch_str[len("compute_"):] + arch_num_str = arch_str[len("compute_"):] elif arch_str.startswith("lto_"): - arch_num = arch_str[len("lto_"):] + arch_num_str = arch_str[len("lto_"):] elif arch_str.startswith("sm_"): - arch_num = arch_str[len("sm_"):] - if arch_num not in cuda_archs: + arch_num_str = arch_str[len("sm_"):] + if arch_num_str not in cuda_archs: fail("{} is not a supported cuda arch".format(arch_str)) - return int(arch_num) + return _create_arch_number(arch_num_str) def _get_stage2_arch_info(code_str): return Stage2ArchInfo( - arch = str(_get_arch_number(code_str)), + arch = _format_arch_number(_get_arch_number(code_str)), virtual = code_str.startswith("compute_"), gpu = code_str.startswith("sm_"), lto = code_str.startswith("lto_"), @@ -48,12 +64,12 @@ def _get_arch_spec(spec_str): codes = codes.split(",") if not virt.startswith("compute_"): fail("expect a virtual architecture, got", virt) - stage1_arch = str(_get_arch_number(virt)) + stage1_arch = _format_arch_number(_get_arch_number(virt)) stage2_archs = [_get_stage2_arch_info(code) for code in codes] else: (codes,) = virtual_codes codes = codes.split(",") - stage1_arch = str(min([_get_arch_number(c) for c in codes])) + stage1_arch = _format_arch_number(min([_get_arch_number(c) for c in codes])) stage2_archs = [_get_stage2_arch_info(code) for code in codes] arch_spec = ArchSpecInfo(stage1_arch = stage1_arch, stage2_archs = stage2_archs) return arch_spec diff --git a/cuda/private/providers.bzl b/cuda/private/providers.bzl index cc0c868a..1c7baad4 100644 --- a/cuda/private/providers.bzl +++ b/cuda/private/providers.bzl @@ -17,7 +17,9 @@ cuda_archs = [ "80", "86", "87", + "89", "90", + "90a", ] Stage2ArchInfo = provider( diff --git a/tests/flag/BUILD.bazel b/tests/flag/BUILD.bazel index 1c0d9bc7..5e6d9cfb 100644 --- a/tests/flag/BUILD.bazel +++ b/tests/flag/BUILD.bazel @@ -11,6 +11,8 @@ load( "cuda_library_compute61_sm61_flag_test", "cuda_library_flag_test", "cuda_library_sm61_flag_test", + "cuda_library_sm90a_flag_test", + "cuda_library_sm90a_sm90_flag_test", "num_actions_test", ) load("@rules_cuda//cuda:defs.bzl", "cuda_library") @@ -311,3 +313,22 @@ cuda_library_compute61_sm61_flag_test( ], target_under_test = "@rules_cuda_examples//basic:kernel", ) + +cuda_library_sm90a_flag_test( + name = "cuda_library_sm90a_arch_flag_test", + action_mnemonic = "CudaCompile", + contain_flags = [ + "-gencode arch=compute_90a,code=sm_90a", + ], + target_under_test = "@rules_cuda_examples//basic:kernel", +) + +cuda_library_sm90a_sm90_flag_test( + name = "cuda_library_sm90a_sm90_arch_flag_test", + action_mnemonic = "CudaCompile", + contain_flags = [ + "-gencode arch=compute_90,code=sm_90", + "-gencode arch=compute_90,code=sm_90a", + ], + target_under_test = "@rules_cuda_examples//basic:kernel", +) diff --git a/tests/flag/flag_validation_test.bzl b/tests/flag/flag_validation_test.bzl index 10318770..9ed4e00c 100644 --- a/tests/flag/flag_validation_test.bzl +++ b/tests/flag/flag_validation_test.bzl @@ -92,8 +92,12 @@ config_settings_sm61 = {"@//cuda:archs": "sm_61"} config_settings_compute60 = {"@//cuda:archs": "compute_60"} config_settings_compute60_sm61 = {"@//cuda:archs": "compute_60,sm_61"} config_settings_compute61_sm61 = {"@//cuda:archs": "compute_61,sm_61"} +config_settings_sm90a = {"@//cuda:archs": "sm_90a"} +config_settings_sm90a_sm90 = {"@//cuda:archs": "sm_90a,sm_90"} cuda_library_sm61_flag_test = _create_cuda_library_flag_test(config_settings_sm61) +cuda_library_sm90a_flag_test = _create_cuda_library_flag_test(config_settings_sm90a) +cuda_library_sm90a_sm90_flag_test = _create_cuda_library_flag_test(config_settings_sm90a_sm90) cuda_library_compute60_flag_test = _create_cuda_library_flag_test(config_settings_compute60) cuda_library_compute60_sm61_flag_test = _create_cuda_library_flag_test(config_settings_compute60_sm61) cuda_library_compute61_sm61_flag_test = _create_cuda_library_flag_test(config_settings_compute61_sm61) From 10727055965528823510c5a21f1e552697c2bd45 Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Sat, 1 Jul 2023 14:39:59 +0800 Subject: [PATCH 32/43] chore(deps): update dependency mkdocs-material to v9.1.17 (#116) --- docs/requirements.txt | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/requirements.txt b/docs/requirements.txt index 71599d29..bd1d9215 100644 --- a/docs/requirements.txt +++ b/docs/requirements.txt @@ -1 +1 @@ -mkdocs-material==9.1.15 +mkdocs-material==9.1.17 From 7ab40f0a2789ffdac0895621897d710bc425c5b7 Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Sat, 1 Jul 2023 14:40:21 +0800 Subject: [PATCH 33/43] chore(deps): update dependency bazel to v6.2.1 (#115) --- .bazelversion | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.bazelversion b/.bazelversion index 6abaeb2f..024b066c 100644 --- a/.bazelversion +++ b/.bazelversion @@ -1 +1 @@ -6.2.0 +6.2.1 From 09e10b36f02c2e4bca81a7a8c77b094ccc59aa87 Mon Sep 17 00:00:00 2001 From: "renovate[bot]" <29139614+renovate[bot]@users.noreply.github.com> Date: Sat, 1 Jul 2023 14:41:04 +0800 Subject: [PATCH 34/43] chore(deps): update dependency bazel_skylib to v1.4.2 (#117) --- MODULE.bazel | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/MODULE.bazel b/MODULE.bazel index 8de8f6b0..4eace12b 100644 --- a/MODULE.bazel +++ b/MODULE.bazel @@ -4,7 +4,7 @@ module( version = "0.0.0", ) -bazel_dep(name = "bazel_skylib", version = "1.2.1") +bazel_dep(name = "bazel_skylib", version = "1.4.2") bazel_dep(name = "platforms", version = "0.0.6") toolchain = use_extension("@rules_cuda//cuda:extensions.bzl", "toolchain") From e49f414bcd9cc4baa7226979ca0d80aa308f9979 Mon Sep 17 00:00:00 2001 From: cloudhan Date: Tue, 4 Jul 2023 04:40:30 +0800 Subject: [PATCH 35/43] Ignore MODULE.bazel for renovate bot (#118) --- renovate.json | 1 + 1 file changed, 1 insertion(+) diff --git a/renovate.json b/renovate.json index 66f08137..1eed7db3 100644 --- a/renovate.json +++ b/renovate.json @@ -1,5 +1,6 @@ { "$schema": "https://docs.renovatebot.com/renovate-schema.json", "extends": ["config:base"], + "ignorePaths": ["MODULE.bazel"], "schedule": ["on the first day of the month"] } From 22578d72e9e026b8847b52c80e6bc8369fa2639c Mon Sep 17 00:00:00 2001 From: Gary Miguel Date: Thu, 6 Jul 2023 03:58:23 -0700 Subject: [PATCH 36/43] Include versioned so files in cuda_runtime (#114) libcudart.so is a symlink to a versioned .so file, and the SONAME specifies the versioned file, which means that at runtime the dynamic linker will look for the versioned file. Without a version suffix in .so file, the dynamic linker will not be able to resolve the library correctly in a multi-versioned CUDA installation environment. Fixes: #113 --- cuda/defs.bzl | 4 ++- cuda/private/os_helpers.bzl | 26 +++++++++++++++++++ cuda/runtime/BUILD.local_cuda | 49 +++++++++++++---------------------- 3 files changed, 47 insertions(+), 32 deletions(-) diff --git a/cuda/defs.bzl b/cuda/defs.bzl index ba1aa4ab..70459824 100644 --- a/cuda/defs.bzl +++ b/cuda/defs.bzl @@ -3,7 +3,7 @@ Core rules for building CUDA projects. """ load("//cuda/private:providers.bzl", _CudaArchsInfo = "CudaArchsInfo", _cuda_archs = "cuda_archs") -load("//cuda/private:os_helpers.bzl", _if_linux = "if_linux", _if_windows = "if_windows") +load("//cuda/private:os_helpers.bzl", _cc_import_versioned_sos = "cc_import_versioned_sos", _if_linux = "if_linux", _if_windows = "if_windows") load("//cuda/private:rules/cuda_objects.bzl", _cuda_objects = "cuda_objects") load("//cuda/private:rules/cuda_library.bzl", _cuda_library = "cuda_library") load("//cuda/private:rules/cuda_toolkit.bzl", _cuda_toolkit = "cuda_toolkit") @@ -33,3 +33,5 @@ cuda_library = _cuda_library if_linux = _if_linux if_windows = _if_windows + +cc_import_versioned_sos = _cc_import_versioned_sos diff --git a/cuda/private/os_helpers.bzl b/cuda/private/os_helpers.bzl index f9068a3e..50bcf73e 100644 --- a/cuda/private/os_helpers.bzl +++ b/cuda/private/os_helpers.bzl @@ -1,3 +1,5 @@ +load("@bazel_skylib//lib:paths.bzl", "paths") + def if_linux(if_true, if_false = []): return select({ "@platforms//os:linux": if_true, @@ -9,3 +11,27 @@ def if_windows(if_true, if_false = []): "@platforms//os:windows": if_true, "//conditions:default": if_false, }) + +def cc_import_versioned_sos(name, shared_library): + """Creates a cc_library that depends on all versioned .so files with the given prefix. + + If is path/to/foo.so, and it is a symlink to foo.so., + this should be used instead of cc_import. + The versioned files are typically needed at runtime, but not at build time. + + Args: + name: Name of the cc_library. + shared_library: Prefix of the versioned .so files. + """ + so_paths = native.glob([shared_library + "*"]) + + [native.cc_import( + name = paths.basename(p), + shared_library = p, + target_compatible_with = ["@platforms//os:linux"], + ) for p in so_paths] + + native.cc_library( + name = name, + deps = [":%s" % paths.basename(p) for p in so_paths], + ) diff --git a/cuda/runtime/BUILD.local_cuda b/cuda/runtime/BUILD.local_cuda index a775673f..6f5cae4b 100644 --- a/cuda/runtime/BUILD.local_cuda +++ b/cuda/runtime/BUILD.local_cuda @@ -1,5 +1,4 @@ -load("@rules_cuda//cuda:defs.bzl", "if_linux", "if_windows") -load(":defs.bzl", "if_local_cuda") +load("@rules_cuda//cuda:defs.bzl", "cc_import_versioned_sos", "if_linux", "if_windows") package( default_visibility = ["//visibility:public"], @@ -8,9 +7,9 @@ package( filegroup( name = "compiler_deps", srcs = [ + "cuda/version.txt", ":_cuda_header_files", ] + glob([ - "cuda/version.txt", "cuda/bin/**", "cuda/lib64/**", "cuda/nvvm/**", @@ -39,10 +38,9 @@ cc_library( ]), ) -cc_import( +cc_import_versioned_sos( name = "cudart_so", shared_library = "cuda/lib64/libcudart.so", - target_compatible_with = ["@platforms//os:linux"], ) cc_library( @@ -136,16 +134,14 @@ cc_library( ]), ) -cc_import( +cc_import_versioned_sos( name = "cublas_so", shared_library = "cuda/lib64/libcublas.so", - target_compatible_with = ["@platforms//os:linux"], ) -cc_import( +cc_import_versioned_sos( name = "cublasLt_so", shared_library = "cuda/lib64/libcublasLt.so", - target_compatible_with = ["@platforms//os:linux"], ) cc_import( @@ -193,10 +189,9 @@ cc_library( ) # CUPTI -cc_import( +cc_import_versioned_sos( name = "cupti_so", shared_library = "cuda/lib64/libcupti.so", - target_compatible_with = ["@platforms//os:linux"], ) cc_import( @@ -301,10 +296,9 @@ cc_library( ) # curand -cc_import( +cc_import_versioned_sos( name = "curand_so", shared_library = "cuda/lib64/libcurand.so", - target_compatible_with = ["@platforms//os:linux"], ) cc_import( @@ -351,19 +345,17 @@ cc_library( "cuda/include", ], visibility = ["//visibility:public"], - deps = [] + - if_linux([ - ":nvptxcompiler_so" + deps = [] + if_linux([ + ":nvptxcompiler_so", ]) + if_windows([ - ":nvptxcompiler_lib" - ]) + ":nvptxcompiler_lib", + ]), ) # cufft -cc_import( +cc_import_versioned_sos( name = "cufft_so", shared_library = "cuda/lib64/libcufft.so", - target_compatible_with = ["@platforms//os:linux"], ) cc_import( @@ -373,10 +365,9 @@ cc_import( target_compatible_with = ["@platforms//os:windows"], ) -cc_import( +cc_import_versioned_sos( name = "cufftw_so", shared_library = "cuda/lib64/libcufftw.so", - target_compatible_with = ["@platforms//os:linux"], ) cc_import( @@ -392,7 +383,7 @@ cc_library( ":cuda_headers", ] + if_linux([ ":cufft_so", - ":cufftw_so" + ":cufftw_so", ]) + if_windows([ ":cufft_lib", ":cufftw_lib", @@ -400,10 +391,9 @@ cc_library( ) # cusolver -cc_import( +cc_import_versioned_sos( name = "cusolver_so", shared_library = "cuda/lib64/libcusolver.so", - target_compatible_with = ["@platforms//os:linux"], ) cc_import( @@ -425,10 +415,9 @@ cc_library( ) # cusparse -cc_import( +cc_import_versioned_sos( name = "cusparse_so", shared_library = "cuda/lib64/libcusparse.so", - target_compatible_with = ["@platforms//os:linux"], ) cc_import( @@ -450,10 +439,9 @@ cc_library( ) # nvtx -cc_import( +cc_import_versioned_sos( name = "nvtx_so", shared_library = "cuda/lib64/libnvToolsExt.so", - target_compatible_with = ["@platforms//os:linux"], ) cc_import( @@ -505,10 +493,9 @@ _NPP_LIBS = { } [ - cc_import( + cc_import_versioned_sos( name = name + "_so", shared_library = "cuda/lib64/lib{}.so".format(name), - target_compatible_with = ["@platforms//os:linux"], ) for name in _NPP_LIBS.keys() ] From 33c3843c998b6715dac3dc18b2f3218df3efdb17 Mon Sep 17 00:00:00 2001 From: Gary Miguel Date: Thu, 6 Jul 2023 10:01:56 -0700 Subject: [PATCH 37/43] Support toolkit_path in rules_cuda_dependencies (#121) --- cuda/private/repositories.bzl | 12 ++++++++---- 1 file changed, 8 insertions(+), 4 deletions(-) diff --git a/cuda/private/repositories.bzl b/cuda/private/repositories.bzl index 9a29f4c7..27265722 100644 --- a/cuda/private/repositories.bzl +++ b/cuda/private/repositories.bzl @@ -50,7 +50,7 @@ def detect_cuda_toolkit(repository_ctx): # Some distributions instead put CUDA binaries in a seperate path # Manually check and redirect there when necessary - alternative = repository_ctx.path('/usr/lib/nvidia-cuda-toolkit/bin/nvcc') + alternative = repository_ctx.path("/usr/lib/nvidia-cuda-toolkit/bin/nvcc") if str(ptxas_path) == "/usr/bin/ptxas" and alternative.exists: ptxas_path = alternative cuda_path = str(ptxas_path.dirname.dirname) @@ -206,8 +206,12 @@ local_cuda = repository_rule( # remotable = True, ) -def rules_cuda_dependencies(): - """Populate the dependencies for rules_cuda. This will setup workspace dependencies (other bazel rules) and local toolchains.""" +def rules_cuda_dependencies(toolkit_path = None): + """Populate the dependencies for rules_cuda. This will setup workspace dependencies (other bazel rules) and local toolchains. + + Args: + toolkit_path: Optionally specify the path to CUDA toolkit. If not specified, it will be detected automatically. + """ maybe( name = "bazel_skylib", repo_rule = http_archive, @@ -228,4 +232,4 @@ def rules_cuda_dependencies(): ], ) - local_cuda(name = "local_cuda") + local_cuda(name = "local_cuda", toolkit_path = toolkit_path) From 090f403e1747e03e7bcc1495fd1ef1fabcf9f3d1 Mon Sep 17 00:00:00 2001 From: Gary Miguel Date: Thu, 6 Jul 2023 17:38:23 -0700 Subject: [PATCH 38/43] Apply some pre-commit fixes (#124) --- .github/workflows/build-tests.yaml | 6 +++++- docs/mkdocs/stylesheets/extra.css | 2 +- examples/if_cuda/README.md | 12 +++++++++--- 3 files changed, 15 insertions(+), 5 deletions(-) diff --git a/.github/workflows/build-tests.yaml b/.github/workflows/build-tests.yaml index ac75c639..5703a417 100644 --- a/.github/workflows/build-tests.yaml +++ b/.github/workflows/build-tests.yaml @@ -16,7 +16,11 @@ jobs: cases: - { os: "ubuntu-20.04", cuda-version: "11.2.2", source: "nvidia" } - { os: "ubuntu-20.04", cuda-version: "11.6.2", source: "nvidia" } - - { os: "ubuntu-22.04", cuda-version: "11.5.1-1ubuntu1", source: "ubuntu" } + - { + os: "ubuntu-22.04", + cuda-version: "11.5.1-1ubuntu1", + source: "ubuntu", + } - { os: "windows-2019", cuda-version: "10.1.243", source: "nvidia" } - { os: "windows-2019", cuda-version: "11.6.2", source: "nvidia" } steps: diff --git a/docs/mkdocs/stylesheets/extra.css b/docs/mkdocs/stylesheets/extra.css index 58ac8189..ced394ba 100644 --- a/docs/mkdocs/stylesheets/extra.css +++ b/docs/mkdocs/stylesheets/extra.css @@ -1,5 +1,5 @@ .md-header { - background: #44a147 + background: #44a147; } .stardoc-pre { diff --git a/examples/if_cuda/README.md b/examples/if_cuda/README.md index b3ca8e45..ce35b973 100644 --- a/examples/if_cuda/README.md +++ b/examples/if_cuda/README.md @@ -3,7 +3,7 @@ This example demonstrates how to conditionally include CUDA targets in your build. By default, _rules_cuda_ rules are enabled. Disabling rules_cuda rules can be accomplished by passing the `@rules_cuda//cuda:enable` -flag at the command-line or via `.bazelrc`. +flag at the command-line or via `.bazelrc`. ## Building Example with rules_cuda @@ -14,16 +14,19 @@ bazel build //if_cuda:main ``` And run the binary: + ```bash ./bazel-bin/if_cuda/main ``` If a valid GPU device is running on your development machine, the application will exit successfully and print: + ``` cuda enabled ``` If running without a valid GPU device, the code, as written, will print a CUDA error and exit: + ``` CUDA_VISIBLE_DEVICES=-1 ./bazel-bin/if_cuda/main CUDA Error Code : 100 @@ -39,18 +42,20 @@ bazel build //if_cuda:main --@rules_cuda//cuda:enable` ``` And run the binary: + ```bash ./bazel-bin/if_cuda/main ``` The binary will output: + ``` cuda disabled ``` ### rules_cuda targets -Any attempt to build a rules_cuda-defined rule (e.g. `cuda_library` or `cuda_objects`) will _FAIL_ if rules_cuda is disabled, as the CUDA toolchain will not be registered for that invocation. +Any attempt to build a `rules_cuda`-defined rule (e.g. `cuda_library` or `cuda_objects`) will _FAIL_ if `rules_cuda` is disabled, as the CUDA toolchain will not be registered for that invocation. ``` bazel build //if_cuda:kernel --@rules_cuda//cuda:enable=false @@ -64,6 +69,7 @@ FAILED: Build did NOT complete successfully (0 packages loaded, 133 targets conf ## Developing for CUDA- and CUDA-free targets Note the `BUILD.bazel` file takes care to ensure that + - CUDA-related dependencies are excluded when CUDA is disabled - Preprocessor variables are set to enable compile-time differentiated codepaths between CUDA and non-CUDA builds @@ -78,4 +84,4 @@ select({ }) ``` -We use this same mechanism to include the `cuda_library` dependencies. \ No newline at end of file +We use this same mechanism to include the `cuda_library` dependencies. From 71b85abfb70753dbe708022b34717b36d4246c3d Mon Sep 17 00:00:00 2001 From: Gary Miguel Date: Fri, 7 Jul 2023 07:48:16 -0700 Subject: [PATCH 39/43] Run pre-commit in GitHub check (#122) --- .github/workflows/build-tests.yaml | 1 + .github/workflows/pre-commit.yaml | 22 ++++++++++++++++++++++ 2 files changed, 23 insertions(+) create mode 100644 .github/workflows/pre-commit.yaml diff --git a/.github/workflows/build-tests.yaml b/.github/workflows/build-tests.yaml index 5703a417..6d508e38 100644 --- a/.github/workflows/build-tests.yaml +++ b/.github/workflows/build-tests.yaml @@ -85,3 +85,4 @@ jobs: - run: cd examples && bazelisk build //if_cuda:main --enable_cuda=False --config=bzlmod - run: bazelisk shutdown + diff --git a/.github/workflows/pre-commit.yaml b/.github/workflows/pre-commit.yaml new file mode 100644 index 00000000..4e95b645 --- /dev/null +++ b/.github/workflows/pre-commit.yaml @@ -0,0 +1,22 @@ +name: pre-commit + +on: + push: + branches: + - main + pull_request: + +jobs: + pre-commit: + runs-on: ubuntu-22.04 + steps: + - uses: actions/checkout@v3 + - name: set PY + run: echo "PY=$(python -VV | sha256sum | cut -d' ' -f1)" >> $GITHUB_ENV + - uses: actions/cache@v1 + with: + path: ~/.cache/pre-commit + key: pre-commit|${{ env.PY }}|${{ hashFiles('.pre-commit-config.yaml') }} + - uses: pre-commit/action@v3.0.0 + - uses: pre-commit-ci/lite-action@v1.0.1 + if: always() From b5a38645b77603c938779d0104e9b421e36cd0ff Mon Sep 17 00:00:00 2001 From: cloudhan Date: Fri, 7 Jul 2023 23:02:01 +0800 Subject: [PATCH 40/43] Format to fix precommit (#126) --- .github/workflows/build-tests.yaml | 1 - cuda/private/actions/compile.bzl | 3 ++- cuda/private/rules/flags.bzl | 4 ++-- examples/if_cuda/BUILD.bazel | 6 +++--- 4 files changed, 7 insertions(+), 7 deletions(-) diff --git a/.github/workflows/build-tests.yaml b/.github/workflows/build-tests.yaml index 6d508e38..5703a417 100644 --- a/.github/workflows/build-tests.yaml +++ b/.github/workflows/build-tests.yaml @@ -85,4 +85,3 @@ jobs: - run: cd examples && bazelisk build //if_cuda:main --enable_cuda=False --config=bzlmod - run: bazelisk shutdown - diff --git a/cuda/private/actions/compile.bzl b/cuda/private/actions/compile.bzl index 44f3ed76..644dbc39 100644 --- a/cuda/private/actions/compile.bzl +++ b/cuda/private/actions/compile.bzl @@ -44,7 +44,7 @@ def compile( basename = cuda_helper.get_basename_without_ext(src.basename, ALLOW_CUDA_SRCS, fail_if_not_match = False) if not basename: continue - basename_index = basename_counter.setdefault(basename, default=0) + basename_index = basename_counter.setdefault(basename, default = 0) basename_counter[basename] += 1 src_and_indexed_basenames.append((src, basename, basename_index)) @@ -52,6 +52,7 @@ def compile( for src, basename, basename_index in src_and_indexed_basenames: filename = None filename = cuda_helper.get_artifact_name(cuda_toolchain, artifact_category_name, basename) + # Objects are placed in _objs//. # For files with the same basename, say srcs = ["kernel.cu", "foo/kernel.cu", "bar/kernel.cu"], we get # _objs//0/kernel., _objs//1/kernel., _objs//2/kernel.. diff --git a/cuda/private/rules/flags.bzl b/cuda/private/rules/flags.bzl index f76648fb..14e4da4e 100644 --- a/cuda/private/rules/flags.bzl +++ b/cuda/private/rules/flags.bzl @@ -49,8 +49,8 @@ Best Practices: def _repeatable_string_flag_impl(ctx): flags = ctx.build_setting_value - if(flags == [""]): - flags = [] + if (flags == [""]): + flags = [] return BuildSettingInfo(value = flags) repeatable_string_flag = rule( diff --git a/examples/if_cuda/BUILD.bazel b/examples/if_cuda/BUILD.bazel index 9c920f5d..bbe313fb 100644 --- a/examples/if_cuda/BUILD.bazel +++ b/examples/if_cuda/BUILD.bazel @@ -11,10 +11,10 @@ cc_binary( srcs = ["main.cpp"], defines = [] + select({ "@rules_cuda//cuda:is_enabled": ["CUDA_ENABLED"], - "//conditions:default": ["CUDA_DISABLED"] + "//conditions:default": ["CUDA_DISABLED"], }), deps = [] + select({ "@rules_cuda//cuda:is_enabled": [":kernel"], - "//conditions:default": [] - }) + "//conditions:default": [], + }), ) From 039ee7bf59790e4d8e7c279d298f618ab5b3d2b5 Mon Sep 17 00:00:00 2001 From: Gary Miguel Date: Fri, 7 Jul 2023 08:10:45 -0700 Subject: [PATCH 41/43] Set nvcc --generate-line-info when compilation_mode=fastbuild (#120) This makes the debug info for both host and device code the same (i.e. --generate-line-info does for device code what -g1 does for host code). Change-Id: I9b3c9afad4b5c9275076fde4462225594c37304b --- cuda/private/toolchain_configs/nvcc.bzl | 2 +- tests/flag/BUILD.bazel | 5 ++++- 2 files changed, 5 insertions(+), 2 deletions(-) diff --git a/cuda/private/toolchain_configs/nvcc.bzl b/cuda/private/toolchain_configs/nvcc.bzl index 66cba5cf..3dd5cd84 100644 --- a/cuda/private/toolchain_configs/nvcc.bzl +++ b/cuda/private/toolchain_configs/nvcc.bzl @@ -331,7 +331,7 @@ def _impl(ctx): flag_sets = [ flag_set( actions = [ACTION_NAMES.cuda_compile], - flag_groups = [flag_group(flags = ["-Xcompiler", "-g1"])], + flag_groups = [flag_group(flags = ["--generate-line-info", "-Xcompiler", "-g1"])], ), ], provides = ["compilation_mode"], diff --git a/tests/flag/BUILD.bazel b/tests/flag/BUILD.bazel index 5e6d9cfb..dd51621e 100644 --- a/tests/flag/BUILD.bazel +++ b/tests/flag/BUILD.bazel @@ -47,7 +47,10 @@ cuda_library_c_dbg_flag_test( cuda_library_c_fastbuild_flag_test( name = "cuda_library_c_fastbuild_flag_test", action_mnemonic = "CudaCompile", - contain_flags = ["-g1"], + contain_flags = [ + "--generate-line-info", + "-g1", + ], not_contain_flags = ["-DNDEBUG"], target_compatible_with = ["@platforms//os:linux"], target_under_test = "@rules_cuda_examples//basic:kernel", From b9cf8ece9d592c73e8e5944ebf3bc2a15eed2033 Mon Sep 17 00:00:00 2001 From: Gary Miguel Date: Sun, 9 Jul 2023 18:32:11 -0700 Subject: [PATCH 42/43] upgrade buildifier (#127) * Use different buildifier pre-commit The previous one didn't seem to work when I ran it locally. Maybe a newer version of it would, but that one doesn't seem to cache the buildifier binary which seems like it will be a lot slower. This also updates to the latest version of buildifier Change-Id: Ifeec1bc6a9663619b74f7cafb1be6eb2eecf9b61 * Format with newest buildifier Change-Id: I74fb2d01863b68ad3274bb0e0e70b3350f53e50a --- .pre-commit-config.yaml | 7 +++---- cuda/templates/BUILD.local_toolchain_clang | 10 +++++----- cuda/templates/BUILD.local_toolchain_nvcc | 5 +++-- cuda/templates/BUILD.local_toolchain_nvcc_msvc | 5 +++-- examples/WORKSPACE.bazel | 3 ++- 5 files changed, 16 insertions(+), 14 deletions(-) diff --git a/.pre-commit-config.yaml b/.pre-commit-config.yaml index 9b963958..c03ca647 100644 --- a/.pre-commit-config.yaml +++ b/.pre-commit-config.yaml @@ -11,11 +11,10 @@ default_stages: [commit] repos: # Check formatting and lint for starlark code - - repo: https://github.com/keith/pre-commit-buildifier - rev: 4.0.1.1 + - repo: https://github.com/garymm/bazel-buildifier-pre-commit-hooks + rev: v6.1.2 hooks: - - id: buildifier - # - id: buildifier-lint + - id: bazel-buildifier # Enforce that commit messages allow for later changelog generation - repo: https://github.com/commitizen-tools/commitizen rev: v2.18.0 diff --git a/cuda/templates/BUILD.local_toolchain_clang b/cuda/templates/BUILD.local_toolchain_clang index 1ef17940..903f6377 100644 --- a/cuda/templates/BUILD.local_toolchain_clang +++ b/cuda/templates/BUILD.local_toolchain_clang @@ -2,19 +2,19 @@ load( "@rules_cuda//cuda:defs.bzl", - "cuda_toolkit", "cuda_toolchain", + "cuda_toolkit", cuda_toolchain_config = "cuda_toolchain_config_clang", ) cuda_toolkit( name = "cuda-toolkit", - path = "%{cuda_path}", - version = "%{cuda_version}", - nvlink = "%{nvlink_label}", - link_stub = "%{link_stub_label}", bin2c = "%{bin2c_label}", fatbinary = "%{fatbinary_label}", + link_stub = "%{link_stub_label}", + nvlink = "%{nvlink_label}", + path = "%{cuda_path}", + version = "%{cuda_version}", ) cuda_toolchain_config( diff --git a/cuda/templates/BUILD.local_toolchain_nvcc b/cuda/templates/BUILD.local_toolchain_nvcc index fde9c3b7..4c18136e 100644 --- a/cuda/templates/BUILD.local_toolchain_nvcc +++ b/cuda/templates/BUILD.local_toolchain_nvcc @@ -20,8 +20,9 @@ cuda_toolkit( cuda_toolchain_config( name = "nvcc-local-config", cuda_toolkit = ":cuda-toolkit", - nvcc_version_major = %{nvcc_version_major}, - nvcc_version_minor = %{nvcc_version_minor}, + # int("%{foo}") instead of %{foo} to make the file valid syntactically. + nvcc_version_major = int("%{nvcc_version_major}"), + nvcc_version_minor = int("%{nvcc_version_minor}"), toolchain_identifier = "nvcc", ) diff --git a/cuda/templates/BUILD.local_toolchain_nvcc_msvc b/cuda/templates/BUILD.local_toolchain_nvcc_msvc index dee4ba5a..7309e18e 100644 --- a/cuda/templates/BUILD.local_toolchain_nvcc_msvc +++ b/cuda/templates/BUILD.local_toolchain_nvcc_msvc @@ -21,8 +21,9 @@ cuda_toolchain_config( name = "nvcc-local-config", cuda_toolkit = ":cuda-toolkit", msvc_env_tmp = "%{env_tmp}", - nvcc_version_major = %{nvcc_version_major}, - nvcc_version_minor = %{nvcc_version_minor}, + # int("%{foo}") instead of %{foo} to make the file valid syntactically. + nvcc_version_major = int("%{nvcc_version_major}"), + nvcc_version_minor = int("%{nvcc_version_minor}"), toolchain_identifier = "nvcc", ) diff --git a/examples/WORKSPACE.bazel b/examples/WORKSPACE.bazel index 3f9cfe2d..f79eaaf7 100644 --- a/examples/WORKSPACE.bazel +++ b/examples/WORKSPACE.bazel @@ -13,6 +13,7 @@ local_repository( # you should fetch it *before* calling this. load("@rules_cuda//cuda:repositories.bzl", "register_detected_cuda_toolchains", "rules_cuda_dependencies") + rules_cuda_dependencies() -register_detected_cuda_toolchains() +register_detected_cuda_toolchains() From 555f88f718579114ace33401de637833eef80ebb Mon Sep 17 00:00:00 2001 From: Gary Miguel Date: Wed, 12 Jul 2023 18:37:32 -0700 Subject: [PATCH 43/43] Have cuda_library output RDC (#125) This allows a `cuda_library` that was built with `rdc=True` to be depended upon by another such library. This is convenient as such a library can be consumed by either another `cuda_library` OR a `cc_library`. Change-Id: I1014d28a0ab3a9c76b788821211b13c4a9956d2a --- .github/workflows/build-tests.yaml | 8 +++--- cuda/private/rules/cuda_library.bzl | 22 ++++++++++++++-- examples/rdc/BUILD.bazel | 39 +++++++++++++++++++++++------ 3 files changed, 55 insertions(+), 14 deletions(-) diff --git a/.github/workflows/build-tests.yaml b/.github/workflows/build-tests.yaml index 5703a417..43015ba3 100644 --- a/.github/workflows/build-tests.yaml +++ b/.github/workflows/build-tests.yaml @@ -74,13 +74,13 @@ jobs: if: ${{ startsWith(matrix.cases.os, 'windows') }} run: .github/workflows/Set-VSEnv.ps1 2019 - - run: bazelisk build @rules_cuda_examples//basic:main - - run: bazelisk build @rules_cuda_examples//rdc:main + - run: bazelisk build @rules_cuda_examples//basic:all + - run: bazelisk build @rules_cuda_examples//rdc:all - run: bazelisk build @rules_cuda_examples//if_cuda:main - run: bazelisk build @rules_cuda_examples//if_cuda:main --enable_cuda=False - - run: cd examples && bazelisk build //basic:main --config=bzlmod - - run: cd examples && bazelisk build //rdc:main --config=bzlmod + - run: cd examples && bazelisk build //basic:all --config=bzlmod + - run: cd examples && bazelisk build //rdc:all --config=bzlmod - run: cd examples && bazelisk build //if_cuda:main --config=bzlmod - run: cd examples && bazelisk build //if_cuda:main --enable_cuda=False --config=bzlmod diff --git a/cuda/private/rules/cuda_library.bzl b/cuda/private/rules/cuda_library.bzl index 75c2360c..bdb40127 100644 --- a/cuda/private/rules/cuda_library.bzl +++ b/cuda/private/rules/cuda_library.bzl @@ -31,13 +31,17 @@ def _cuda_library_impl(ctx): # outputs objects = depset(compile(ctx, cuda_toolchain, cc_toolchain, src_files, common, pic = False, rdc = use_rdc)) pic_objects = depset(compile(ctx, cuda_toolchain, cc_toolchain, src_files, common, pic = True, rdc = use_rdc)) + rdc_objects = depset([]) + rdc_pic_objects = depset([]) # if rdc is enabled for this cuda_library, then we need futher do a pass of device link if use_rdc: transitive_objects = depset(transitive = [dep[CudaInfo].rdc_objects for dep in attr.deps if CudaInfo in dep]) transitive_pic_objects = depset(transitive = [dep[CudaInfo].rdc_pic_objects for dep in attr.deps if CudaInfo in dep]) objects = depset(transitive = [objects, transitive_objects]) + rdc_objects = objects pic_objects = depset(transitive = [pic_objects, transitive_pic_objects]) + rdc_pic_objects = pic_objects dlink_object = depset([device_link(ctx, cuda_toolchain, cc_toolchain, objects, common, pic = False, rdc = use_rdc)]) dlink_pic_object = depset([device_link(ctx, cuda_toolchain, cc_toolchain, pic_objects, common, pic = True, rdc = use_rdc)]) objects = depset(transitive = [objects, dlink_object]) @@ -87,12 +91,20 @@ def _cuda_library_impl(ctx): pic_lib = pic_libs, objects = objects, pic_objects = pic_objects, + rdc_objects = rdc_objects, + rdc_pic_objects = rdc_pic_objects, ), CcInfo( compilation_context = cc_info.compilation_context, linking_context = cc_info.linking_context, ), - cuda_helper.create_cuda_info(defines = depset(common.defines)), + cuda_helper.create_cuda_info( + defines = depset(common.defines), + objects = objects, + pic_objects = pic_objects, + rdc_objects = rdc_objects, + rdc_pic_objects = rdc_pic_objects, + ), ] cuda_library = rule( @@ -104,7 +116,13 @@ cuda_library = rule( "hdrs": attr.label_list(allow_files = ALLOW_CUDA_HDRS), "deps": attr.label_list(providers = [[CcInfo], [CudaInfo]]), "alwayslink": attr.bool(default = False), - "rdc": attr.bool(default = False, doc = "whether to perform relocateable device code linking, otherwise, normal device link."), + "rdc": attr.bool( + default = False, + doc = ("Whether to produce and consume relocateable device code. " + + "Transitive deps that contain device code must all either be cuda_objects or cuda_library(rdc = True). " + + "If False, all device code must be in the same translation unit. May have performance implications. " + + "See https://docs.nvidia.com/cuda/cuda-compiler-driver-nvcc/index.html#using-separate-compilation-in-cuda."), + ), "includes": attr.string_list(doc = "List of include dirs to be added to the compile line."), "host_copts": attr.string_list(doc = "Add these options to the CUDA host compilation command."), "host_defines": attr.string_list(doc = "List of defines to add to the compile line."), diff --git a/examples/rdc/BUILD.bazel b/examples/rdc/BUILD.bazel index 2775d7f6..a4153b88 100644 --- a/examples/rdc/BUILD.bazel +++ b/examples/rdc/BUILD.bazel @@ -1,29 +1,52 @@ load("@rules_cuda//cuda:defs.bzl", "cuda_library", "cuda_objects") cuda_objects( - name = "a", + name = "a_objects", srcs = ["a.cu"], deps = [":b"], ) cuda_objects( - name = "b", + name = "b_objects", srcs = ["b.cu"], hdrs = ["b.cuh"], ) cuda_library( - name = "librdc", - rdc = 1, + name = "lib_from_objects", + rdc = True, deps = [ - ":a", - ":b", + ":a_objects", + ":b_objects", ], ) cc_binary( - name = "main", + name = "main_from_objects", deps = [ - ":librdc", + ":lib_from_objects", + ], +) + +# Another way of doing it is to just use cuda_library +cuda_library( + name = "a", + srcs = ["a.cu"], + rdc = True, + deps = [":b"], +) + +cuda_library( + name = "b", + srcs = ["b.cu"], + hdrs = ["b.cuh"], + rdc = True, +) + +cc_binary( + name = "main_from_library", + deps = [ + ":a", + ":b", ], )