---
title: Rustup - Origins and aliases
...
# Situation
Currently Rustup concerns itself with providing Rust toolchains and components
from a single origin, that of the rust-lang project. It provides these
toolchains in three logical channels (`stable`, `beta`, and `nightly`) along
with more specific channels (`x.yy.zz`, `x.yy`, `nnnnnn-yyyy-mm-dd`). These
toolchains are provided with architecture, operating system, and environment
values; and Rustup permits elision of up to all but the channel name, filling in
gaps based on the host platform and other information.
Once installed, Rustup refers to these toolchains by their channel and where
necessary, some of the architecture/os/environment information to disambiguate.
These channels are provided by means of manifest files present in a particular
directory structure on the `RUSTUP_DIST_SERVER` (typically static.rlo). Channel
manifests are signed with the Rust project's OpenPGP key, and they contain hash
sums which provides a mechanism to validate components as they are downloaded.
Rustup contains a copy of this key, and defaults for the distribution server, as
well as definitions of the ways channel names are formed.
# Origins
If we group together a dist server URL base, a signing key, and a "name" of some
sort, we get the concept referred to in this document as an "Origin".
Current Rustup effectively supports only a single Origin as described in the
situation section at the start of this document.
The proposal here is to permit Rustup to support multiple Origins, ideally
dynamically, permitting the user to acquire toolchains from places other than
static.rlo without needing to faff with permanently adjusting environment
variables.
## Use-cases
There are two use-cases which spring to mind - the first is that of Amazon, or
any other large company who might produce toolchains internally as part of a
software-supply-chain thing. For these companies, being able to use "stock"
Rustup may be of value because they may need to compare the results of their
toolchains against officially released ones, perhaps internally they only
provide `stable` but sometimes a developer needs a `nightly` from rust-lang.
Another use-case which arises is that of a toolchain provider, who may wish to
permit their toolchain to be consumed by a user of Rustup. in that context the
user may wish to have a `rust-toolchain.toml` which requires that not only is it
1.64.0 which is used to build the software, but that it comes from the specific
alternative Origin.
# Approach
Rustup has, built in, some number of Origins (one or more, by default just the
rust-lang Origin) which it can trust. In addition, since you can provide keys
to Rustup, it can use those keys to validate additional Origin specifications.
Each Origin which Rustup knows about can be used to acquire toolchains, and
any toolchain installed from any Origin can be used in the normal way.
Just like Rustup has the concept of a default toolchain, you can also set a
default Origin to use, permitting the use of short names such as `stable`.
To facilitate this, the `toolchains` directory in `RUSTUP_HOME` will be altered
so that instead of `channel-arch-os-env` the toolchain directories will be named
`dist.origin.channel-arch-os-env` where the `origin` is the official name of the
Origin (part of the specification) and `dist` is literal.
## Example specifications
```toml
[origin]
name = "rust-lang"
about = "The official Rust releases from rust-lang"
dist-base = "https://static.rust-lang.org/dist/"
signing-keys = ["""
-----BEGIN PGP PUBLIC KEY BLOCK-----
Version: GnuPG v1
mQINBFJEwMkBEADlPACa2K7reD4x5zd8afKx75QYKmxqZwywRbgeICeD4bKiQoJZ
dUjmn1LgrGaXuBMKXJQhyA34e/1YZel/8et+HPE5XpljBfNYXWbVocE1UMUTnFU9
CKXa4AhJ33f7we2/QmNRMUifw5adPwGMg4D8cDKXk02NdnqQlmFByv0vSaArR5kn
gZKnLY6o0zZ9Buyy761Im/ShXqv4ATUgYiFc48z33G4j+BDmn0ryGr1aFdP58tHp
gjWtLZs0iWeFNRDYDje6ODyu/MjOyuAWb2pYDH47Xu7XedMZzenH2TLM9yt/hyOV
xReDPhvoGkaO8xqHioJMoPQi1gBjuBeewmFyTSPS4deASukhCFOcTsw/enzJagiS
.......
rOY/Ghegvn7fDrnt2KC9MpgeFBXzUp+k5rzUdF8jbCx5apVjA1sWXB9Kh3L+DUwF
Mve696B5tlHyc1KxjHR6w9GRsh4=
=5FXw
-----END PGP PUBLIC KEY BLOCK-----
"""]
```
The specification must be a TOML file, with an accompanying signature file which
must come from a key that Rustup trusts. Channel manifests acquired from a
Origin must be signed by any of the keys listed in the Origin specification. It
is acceptable for these to be the same keys, though that may be considered
redundant. Rustup, once it has acquired an Origin specification, will trust it;
as such, Origins can be injected directly into Rustup's configuration, perhaps as
part of system-wide config in an enterprise.
## Worked example
Here, a user downloads Rustup through the normal means, but opts to not install
any toolchain
```console
$ curl https://sh.rustup.rs/ | sh -s -- --default-toolchain none -y
...
$
```
Next the user provides to Rustup a key they trust to sign Origins
```console
$ rustup origin trust /path/to/signing-key.asc
info: Added trust root: Special Enterprise Rust Release Team <rust@enterprise.com>
$
```
Next the user adds their enterprise's Origin and sets it as the default origin
```console
$ rustup origin add https://rust.internal.enterprise.com/
info: Downloading https://rust.internal.enterprise.com/rust-origin.toml
info: Downloading https://rust.internal.enterprise.com/rust-origin.toml.sig
info: Good signature from Special Enterprise Rust Release Team <rust@enterprise.com>
info: Adding Origin "enterprise"
$ rustup origin list
rust-lang - The official Rust releases from rust-lang (default)
enterprise - Special Enterprise internal Rust releases
$ rustup origin default enterprise
info: Setting default Origin to "enterprise"
$ rustup origin list
rust-lang - The official Rust releases from rust-lang
enterprise - Special Enterprise internal Rust releases (default)
$
```
Finally the user installs the stable release from their enterprise
```console
$ rustup toolchain install stable
info: syncing channel updates for 'enterprise.stable-x86.unknown-linux-gnu'
.....
info: default toolchain set to 'enterprise.stable-x86_64-unknown-linux-gnu'
```
# Aliases
The other main topic for this document is toolchain aliases. We support the
concept of custom toolchains, so in the new schema the `toolchains` directory
would show those as `custom.toolchainname`. These are useful and can be used to
link to arbitrary toolchains on disk, however from time to time it would be
useful to be able to install a dist toolchain but name it in a custom fashion
while still treating it as a dist toolchain.
To facilitate that, we extend the files laid down in a dist toolchain's
`lib/rustlib` slightly. The `multirust-config.toml` has its `config_version`
bumped to `2` and there is an additional section `[meta]` which has
`origin="..."` and `channel="..."` in it to tell Rustup where the channel came
from, as well as `manifest-sha256="..."` which indicates the manifest file's
checksum. With this in place, the `update-hashes` folder becomes obsolete.
Next we introduce `alias.toolchainname` as a top level descriptor which will be
treated as a dist toolchain, but which has the special name given. This
provides for use-cases such as `rust-analyzer` maintaining a toolchain called
`rust-analyzer` which happens to be a `nightly` of some kind, with only the
`rust-analyzer` component installed. a `rustup update` would automatically
update all such channels as though they were normal dist channels.
# Interactions
With custom toolchains, aliased toolchains, and now Origins, the name resolution
for Rustup toolchains becomes a little more complex. The following is the
mechanism by which names are resolved:
1. Is the name an alias, if so, use it.
2. Is the name a custom toolchain, if so use it.
3. Is the given name resolvable with the current default Origin, if so use it
4. Is the given name a fully resolved dist name, if so use it
5. error
It is possible that step 4 could be moved to be step 1, but the important factor
here is that aliased toolchains beat out custom toolchains, though in general
Rustup will do its best to prevent clashes it cannot be guaranteed since the
user may fiddle the filesystem.
```console
$ cargo +enterprise.stable test
...
$ cargo +rust-lang.nightly bench
...
$
```
# Possible other things
* Origins could define channel names permitted from that Origin, allowing for other channel names than stable/beta/nightly
* Origins could potentially specify a proxy URL if they MUST be accessed via such a thing.