1# Table of Contents 2 31. [Contributing to CUB](#contributing-to-cub) 41. [CMake Options](#cmake-options) 51. [Development Model](#development-model) 6 7# Contributing to CUB 8 9CUB uses Github to manage all open-source development, including bug tracking, 10pull requests, and design discussions. This document details how to get 11started as a CUB contributor. 12 13An overview of this process is: 14 151. [Clone the CUB repository](#clone-the-cub-repository) 161. [Setup a fork of CUB](#setup-a-fork-of-cub) 171. [Setup your environment](#setup-your-environment) 181. [Create a development branch](#create-a-development-branch) 191. [Local development loop](#local-development-loop) 201. [Push development branch to your fork](#push-development-branch-to-your-fork) 211. [Create pull request](#create-pull-request) 221. [Address feedback and update pull request](#address-feedback-and-update-pull-request) 231. [When your PR is approved...](#when-your-pr-is-approved) 24 25## Clone the CUB Repository 26 27To get started, clone the main repository to your local computer: 28 29``` 30git clone https://github.com/NVIDIA/cub.git 31cd cub 32``` 33 34## Setup a Fork of CUB 35 36You'll need a fork of CUB on Github to create a pull request. To setup your 37fork: 38 391. Create a Github account (if needed) 402. Go to [the CUB Github page](https://github.com/NVIDIA/cub) 413. Click "Fork" and follow any prompts that appear. 42 43Once your fork is created, setup a new remote repo in your local CUB clone: 44 45``` 46git remote add github-fork git@github.com:<GITHUB_USERNAME>/cub.git 47``` 48 49## Setup Your Environment 50 51### Git Environment 52 53If you haven't already, this is a good time to tell git who you are. This 54information is used to fill out authorship information on your git commits. 55 56``` 57git config --global user.name "John Doe" 58git config --global user.email johndoe@example.com 59``` 60 61### Configure CMake builds 62 63CUB uses [CMake](https://www.cmake.org) for its developer build system. To 64configure, build, and test your checkout of CUB with default settings: 65 66``` 67# Create build directory: 68mkdir build 69cd build 70 71# Configure -- use one of the following: 72cmake .. # Command line interface. 73ccmake .. # ncurses GUI (Linux only) 74cmake-gui # Graphical UI, set source/build directories in the app 75 76# Build: 77cmake --build . -j <num jobs> # invokes make (or ninja, etc) 78 79# Run tests and examples: 80ctest 81``` 82 83See [CMake Options](#cmake-options) for details on customizing the build. 84 85## Create a Development Branch 86 87All work should be done in a development branch (also called a "topic branch") 88and not directly in the `main` branch. This makes it easier to manage multiple 89in-progress patches at once, and provides a descriptive label for your patch 90as it passes through the review system. 91 92To create a new branch based on the current `main`: 93 94``` 95# Checkout local main branch: 96cd /path/to/cub/sources 97git checkout main 98 99# Sync local main branch with github: 100git pull 101 102# Create a new branch named `my_descriptive_branch_name` based on main: 103git checkout -b my_descriptive_branch_name 104 105# Verify that the branch has been created and is currently checked out: 106git branch 107``` 108 109CUB branch names should follow a particular pattern: 110 111- For new features, name the branch `feature/<name>` 112- For bugfixes associated with a github issue, use `bug/github/<bug-description>-<bug-id>` 113 - Internal nvidia and gitlab bugs should use `nvidia` or `gitlab` in place of 114 `github`. 115 116## Local Development Loop 117 118### Edit, Build, Test, Repeat 119 120Once the topic branch is created, you're all set to start working on CUB 121code. Make some changes, then build and test them: 122 123``` 124# Implement changes: 125cd /path/to/cub/sources 126emacs cub/some_file.cuh # or whatever editor you prefer 127 128# Create / update a unit test for your changes: 129emacs tests/some_test.cu 130 131# Check that everything builds and tests pass: 132cd /path/to/cub/build/directory 133cmake --build . -j <num_jobs> # or make, ninja, etc 134ctest 135``` 136 137### Creating a Commit 138 139Once you're satisfied with your patch, commit your changes: 140 141``` 142# Manually add changed files and create a commit: 143cd /path/to/cub 144git add cub/some_file.cuh 145git add tests/some_test.cu 146git commit 147 148# Or, if possible, use git-gui to review your changes while building your patch: 149git gui 150``` 151 152#### Writing a Commit Message 153 154Your commit message will communicate the purpose and rationale behind your 155patch to other developers, and will be used to populate the initial description 156of your Github pull request. 157 158When writing a commit message, the following standard format should be used, 159since tools in the git ecosystem are designed to parse this correctly: 160 161``` 162First line of commit message is a short summary (<80 char) 163<Second line left blank> 164Detailed description of change begins on third line. This portion can 165span multiple lines, try to manually wrap them at something reasonable. 166 167Blank lines can be used to separate multiple paragraphs in the description. 168 169If your patch is associated with another pull request or issue in the main 170CUB repository, you should reference it with a `#` symbol, e.g. 171#1023 for issue 1023. 172 173For issues / pull requests in a different github repo, reference them using 174the full syntax, e.g. NVIDIA/thrust#4 for issue 4 in the NVIDIA/thrust repo. 175 176Markdown is recommended for formatting more detailed messages, as these will 177be nicely rendered on Github, etc. 178``` 179 180## Push Development Branch to your Fork 181 182Once you've committed your changes to a local development branch, it's time to 183push them to your fork: 184 185``` 186cd /path/to/cub/checkout 187git checkout my_descriptive_branch_name # if not already checked out 188git push --set-upstream github-fork my_descriptive_branch_name 189``` 190 191`--set-upstream github-fork` tells git that future pushes/pulls on this branch 192should target your `github-fork` remote by default. 193 194## Create Pull Request 195 196To create a pull request for your freshly pushed branch, open your github fork 197in a browser by going to `https://www.github.com/<GITHUB_USERNAME>/cub`. A 198prompt may automatically appear asking you to create a pull request if you've 199recently pushed a branch. 200 201If there's no prompt, go to "Code" > "Branches" and click the appropriate 202"New pull request" button for your branch. 203 204If you would like a specific developer to review your patch, feel free to 205request them as a reviewer at this time. 206 207The CUB team will review your patch, test it on NVIDIA's internal CI, and 208provide feedback. 209 210## Address Feedback and Update Pull Request 211 212If the reviewers request changes to your patch, use the following process to 213update the pull request: 214 215``` 216# Make changes: 217cd /path/to/cub/sources 218git checkout my_descriptive_branch_name 219emacs cub/some_file.cuh 220emacs tests/some_test.cu 221 222# Build + test 223cd /path/to/thrust/build/directory 224cmake --build . -j <num jobs> 225ctest 226 227# Amend commit: 228cd /path/to/cub/sources 229git add cub/some_file.cuh 230git add tests/some_test.cu 231git commit --amend 232# Or 233git gui # Check the "Amend Last Commit" box 234 235# Update the branch on your fork: 236git push -f 237``` 238 239At this point, the pull request should show your recent changes. 240 241## When Your PR is Approved 242 243Once your pull request is approved by the CUB team, no further action is 244needed from you. We will handle integrating it since we must coordinate changes 245to `main` with NVIDIA's internal perforce repository. 246 247# CMake Options 248 249A CUB build is configured using CMake options. These may be passed to CMake 250using 251 252``` 253cmake -D<option_name>=<value> /path/to/cub/sources 254``` 255 256or configured interactively with the `ccmake` or `cmake-gui` interfaces. 257 258The configuration options for CUB are: 259 260- `CMAKE_BUILD_TYPE={Release, Debug, RelWithDebInfo, MinSizeRel}` 261 - Standard CMake build option. Default: `RelWithDebInfo` 262- `CUB_ENABLE_HEADER_TESTING={ON, OFF}` 263 - Whether to test compile public headers. Default is `ON`. 264- `CUB_ENABLE_TESTING={ON, OFF}` 265 - Whether to build unit tests. Default is `ON`. 266- `CUB_ENABLE_EXAMPLES={ON, OFF}` 267 - Whether to build examples. Default is `ON`. 268- `CUB_ENABLE_DIALECT_CPPXX={ON, OFF}` 269 - Toggle whether a specific C++ dialect will be targeted. 270 - Multiple dialects may be targeted in a single build. 271 - Possible values of `XX` are `{11, 14, 17}`. 272 - By default, only C++14 is enabled. 273- `CUB_ENABLE_COMPUTE_XX={ON, OFF}` 274 - Controls the targeted CUDA architecture(s) 275 - Multiple options may be selected when using NVCC as the CUDA compiler. 276 - Valid values of `XX` are: 277 `{35, 37, 50, 52, 53, 60, 61, 62, 70, 72, 75, 80}` 278 - Default value depends on `CUB_DISABLE_ARCH_BY_DEFAULT`: 279- `CUB_ENABLE_COMPUTE_FUTURE={ON, OFF}` 280 - If enabled, CUDA objects will target the most recent virtual architecture 281 in addition to the real architectures specified by the 282 `CUB_ENABLE_COMPUTE_XX` options. 283 - Default value depends on `CUB_DISABLE_ARCH_BY_DEFAULT`: 284- `CUB_DISABLE_ARCH_BY_DEFAULT={ON, OFF}` 285 - When `ON`, all `CUB_ENABLE_COMPUTE_*` options are initially `OFF`. 286 - Default: `OFF` (meaning all architectures are enabled by default) 287- `CUB_ENABLE_TESTS_WITH_RDC={ON, OFF}` 288 - Whether to enable Relocatable Device Code when building tests. 289 Default is `OFF`. 290- `CUB_ENABLE_EXAMPLES_WITH_RDC={ON, OFF}` 291 - Whether to enable Relocatable Device Code when building examples. 292 Default is `OFF`. 293- `CUB_ENABLE_INSTALL_RULES={ON, OFF}` 294 - If true, installation rules will be generated for CUB. Default is `ON` when 295 building CUB alone, and `OFF` when CUB is a subproject added via CMake's 296 `add_subdirectory`. 297 298# Development Model 299 300The following is a description of the basic development process that CUB follows. This is a living 301document that will evolve as our process evolves. 302 303CUB is distributed in three ways: 304 305 * On GitHub. 306 * In the NVIDIA HPC SDK. 307 * In the CUDA Toolkit. 308 309## Trunk Based Development 310 311CUB uses [trunk based development](https://trunkbaseddevelopment.com). There is a single long-lived 312branch called `main`. Engineers may create branches for feature development. Such branches always 313merge into `main`. There are no release branches. Releases are produced by taking a snapshot of 314`main` ("snapping"). After a release has been snapped from `main`, it will never be changed. 315 316## Repositories 317 318As CUB is developed both on GitHub and internally at NVIDIA, there are three main places where code lives: 319 320 * The Source of Truth, the [public CUB repository](https://github.com/NVIDIA/cub), referred to as 321 `github` later in this document. 322 * An internal GitLab repository, referred to as `gitlab` later in this document. 323 * An internal Perforce repository, referred to as `perforce` later in this document. 324 325## Versioning 326 327CUB has its own versioning system for releases, independent of the versioning scheme of the NVIDIA 328HPC SDK or the CUDA Toolkit. 329 330Today, CUB version numbers have a specific [semantic meaning](https://semver.org/). 331Releases prior to 1.10.0 largely, but not strictly, followed these semantic meanings. 332 333The version number for a CUB release uses the following format: `MMM.mmm.ss-ppp`, where: 334 335 * `CUB_VERSION_MAJOR`/`MMM`: Major version, up to 3 decimal digits. It is incremented 336 when the fundamental nature of the library evolves, leading to widespread changes across the 337 entire library interface with no guarantee of API, ABI, or semantic compatibility with former 338 versions. 339 * `CUB_VERSION_MINOR`/`mmm`: Minor version, up to 3 decimal digits. It is incremented when 340 breaking API, ABI, or semantic changes are made. 341 * `CUB_VERSION_SUBMINOR`/`ss`: Subminor version, up to 2 decimal digits. It is incremented 342 when notable new features or bug fixes or features that are API, ABI, and semantic backwards 343 compatible are added. 344 * `CUB_PATCH_NUMBER`/`ppp`: Patch number, up to 3 decimal digits. It is incremented if any 345 change in the repo whatsoever is made and no other version component has been incremented. 346 347The `<cub/version.h>` header defines `CUB_*` macros for all of the version components mentioned 348above. Additionally, a `CUB_VERSION` macro is defined, which is an integer literal containing all 349of the version components except for `CUB_PATCH_NUMBER`. 350 351## Branches and Tags 352 353The following tag names are used in the CUB project: 354 355 * `github/nvhpc-X.Y`: the tag that directly corresponds to what has been shipped in the NVIDIA HPC SDK release X.Y. 356 * `github/cuda-X.Y`: the tag that directly corresponds to what has been shipped in the CUDA Toolkit release X.Y. 357 * `github/A.B.C`: the tag that directly corresponds to CUB version A.B.C. 358 * `github/A.B.C-rcN`: the tag that directly corresponds to CUB version A.B.C release candidate N. 359 360The following branch names are used in the CUB project: 361 362 * `github/main`: the Source of Truth development branch of CUB. 363 * `github/old-master`: the old Source of Truth branch, before unification of public and internal repositories. 364 * `github/feature/<name>`: feature branch for a feature under development. 365 * `github/bug/<bug-system>/<bug-description>-<bug-id>`: bug fix branch, where `bug-system` is `github` or `nvidia`. 366 * `gitlab/main`: mirror of `github/main`. 367 * `perforce/private`: mirrored `github/main`, plus files necessary for internal NVIDIA testing systems. 368 369On the rare occasion that we cannot do work in the open, for example when developing a change specific to an 370unreleased product, these branches may exist on `gitlab` instead of `github`. By default, everything should be 371in the open on `github` unless there is a strong motivation for it to not be open. 372