Skip to content

Commit 8dfac6f

Browse files
committed
Stabilize automatic garbage collection.
1 parent ea14e86 commit 8dfac6f

File tree

5 files changed

+215
-175
lines changed

5 files changed

+215
-175
lines changed

src/cargo/core/gc.rs

Lines changed: 48 additions & 29 deletions
Original file line numberDiff line numberDiff line change
@@ -49,9 +49,6 @@ const DEFAULT_AUTO_FREQUENCY: &str = "1 day";
4949
/// It should be cheap to call this multiple times (subsequent calls are
5050
/// ignored), but try not to abuse that.
5151
pub fn auto_gc(gctx: &GlobalContext) {
52-
if !gctx.cli_unstable().gc {
53-
return;
54-
}
5552
if !gctx.network_allowed() {
5653
// As a conservative choice, auto-gc is disabled when offline. If the
5754
// user is indefinitely offline, we don't want to delete things they
@@ -176,49 +173,74 @@ impl GcOpts {
176173
let auto_config = gctx
177174
.get::<Option<AutoConfig>>("gc.auto")?
178175
.unwrap_or_default();
179-
self.update_for_auto_gc_config(&auto_config)
176+
self.update_for_auto_gc_config(&auto_config, gctx.cli_unstable().gc)
180177
}
181178

182-
fn update_for_auto_gc_config(&mut self, auto_config: &AutoConfig) -> CargoResult<()> {
179+
fn update_for_auto_gc_config(
180+
&mut self,
181+
auto_config: &AutoConfig,
182+
unstable_allowed: bool,
183+
) -> CargoResult<()> {
184+
macro_rules! config_default {
185+
($auto_config:expr, $field:ident, $default:expr, $unstable_allowed:expr) => {
186+
if !unstable_allowed {
187+
// These config options require -Zgc
188+
$default
189+
} else {
190+
$auto_config.$field.as_deref().unwrap_or($default)
191+
}
192+
};
193+
}
194+
183195
self.max_src_age = newer_time_span_for_config(
184196
self.max_src_age,
185197
"gc.auto.max-src-age",
186-
auto_config
187-
.max_src_age
188-
.as_deref()
189-
.unwrap_or(DEFAULT_MAX_AGE_EXTRACTED),
198+
config_default!(
199+
auto_config,
200+
max_src_age,
201+
DEFAULT_MAX_AGE_EXTRACTED,
202+
unstable_allowed
203+
),
190204
)?;
191205
self.max_crate_age = newer_time_span_for_config(
192206
self.max_crate_age,
193207
"gc.auto.max-crate-age",
194-
auto_config
195-
.max_crate_age
196-
.as_deref()
197-
.unwrap_or(DEFAULT_MAX_AGE_DOWNLOADED),
208+
config_default!(
209+
auto_config,
210+
max_crate_age,
211+
DEFAULT_MAX_AGE_DOWNLOADED,
212+
unstable_allowed
213+
),
198214
)?;
199215
self.max_index_age = newer_time_span_for_config(
200216
self.max_index_age,
201217
"gc.auto.max-index-age",
202-
auto_config
203-
.max_index_age
204-
.as_deref()
205-
.unwrap_or(DEFAULT_MAX_AGE_DOWNLOADED),
218+
config_default!(
219+
auto_config,
220+
max_index_age,
221+
DEFAULT_MAX_AGE_DOWNLOADED,
222+
unstable_allowed
223+
),
206224
)?;
207225
self.max_git_co_age = newer_time_span_for_config(
208226
self.max_git_co_age,
209227
"gc.auto.max-git-co-age",
210-
auto_config
211-
.max_git_co_age
212-
.as_deref()
213-
.unwrap_or(DEFAULT_MAX_AGE_EXTRACTED),
228+
config_default!(
229+
auto_config,
230+
max_git_co_age,
231+
DEFAULT_MAX_AGE_EXTRACTED,
232+
unstable_allowed
233+
),
214234
)?;
215235
self.max_git_db_age = newer_time_span_for_config(
216236
self.max_git_db_age,
217237
"gc.auto.max-git-db-age",
218-
auto_config
219-
.max_git_db_age
220-
.as_deref()
221-
.unwrap_or(DEFAULT_MAX_AGE_DOWNLOADED),
238+
config_default!(
239+
auto_config,
240+
max_git_db_age,
241+
DEFAULT_MAX_AGE_DOWNLOADED,
242+
unstable_allowed
243+
),
222244
)?;
223245
Ok(())
224246
}
@@ -257,9 +279,6 @@ impl<'a, 'gctx> Gc<'a, 'gctx> {
257279
/// This returns immediately without doing work if garbage collection has
258280
/// been performed recently (since `gc.auto.frequency`).
259281
fn auto(&mut self, clean_ctx: &mut CleanContext<'gctx>) -> CargoResult<()> {
260-
if !self.gctx.cli_unstable().gc {
261-
return Ok(());
262-
}
263282
let auto_config = self
264283
.gctx
265284
.get::<Option<AutoConfig>>("gc.auto")?
@@ -278,7 +297,7 @@ impl<'a, 'gctx> Gc<'a, 'gctx> {
278297
return Ok(());
279298
}
280299
let mut gc_opts = GcOpts::default();
281-
gc_opts.update_for_auto_gc_config(&auto_config)?;
300+
gc_opts.update_for_auto_gc_config(&auto_config, self.gctx.cli_unstable().gc)?;
282301
self.gc(clean_ctx, &gc_opts)?;
283302
if !clean_ctx.dry_run {
284303
self.global_cache_tracker.set_last_auto_gc()?;

src/doc/src/reference/config.md

Lines changed: 39 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -95,6 +95,9 @@ ENV_VAR_NAME_3 = { value = "relative/path", relative = true }
9595
[future-incompat-report]
9696
frequency = 'always' # when to display a notification about a future incompat report
9797

98+
[gc.auto]
99+
frequency = "1 day" # How often to perform automatic garbage collection
100+
98101
[cargo-new]
99102
vcs = "none" # VCS to use ('git', 'hg', 'pijul', 'fossil', 'none')
100103

@@ -657,6 +660,42 @@ Controls how often we display a notification to the terminal when a future incom
657660
* `always` (default): Always display a notification when a command (e.g. `cargo build`) produces a future incompat report
658661
* `never`: Never display a notification
659662

663+
### `[gc]`
664+
665+
The `[gc]` table defines settings for garbage collection in Cargo's caches, which will delete old, unused files.
666+
667+
#### `[gc.auto]`
668+
669+
The `[gc.auto]` table defines settings for automatic garbage collection in Cargo's caches.
670+
When running `cargo` commands, Cargo will automatically track which files you are using within the global cache.
671+
Periodically, Cargo will delete files that have not been used for some period of time.
672+
Currently it will delete files that have to be downloaded from the network if they have not been used in 3 months. Files that can be generated without network access will be deleted if they have not been used in 1 month.
673+
674+
The automatic deletion of files only occurs when running commands that are already doing a significant amount of work, such as all of the build commands (`cargo build`, `cargo test`, `cargo check`, etc.), and `cargo fetch`.
675+
676+
Automatic deletion is disabled if cargo is offline such as with `--offline` or `--frozen` to avoid deleting artifacts that may need to be used if you are offline for a long period of time.
677+
678+
> **Note**: This tracking is currently only implemented for the global cache in Cargo's home directory.
679+
> This includes registry indexes and source files downloaded from registries and git dependencies.
680+
> Support for tracking build artifacts is not yet implemented, and tracked in [cargo#13136](https://github.com/rust-lang/cargo/issues/13136).
681+
>
682+
> Additionally, there is an unstable feature to support *manually* triggering garbage collection, and to further customize the configuration options.
683+
> See the [Unstable chapter](unstable.md#gc) for more information.
684+
685+
##### `gc.auto.frequency`
686+
* Type: string
687+
* Default: `"1 day"`
688+
* Environment: `CARGO_GC_AUTO_FREQUENCY`
689+
690+
This option defines how often Cargo will automatically delete unused files in the global cache.
691+
This does *not* define how old the files must be, those thresholds are described [above](#gcauto).
692+
693+
It supports the following settings:
694+
695+
* `"never"` --- Never deletes old files.
696+
* `"always"` --- Checks to delete old files every time Cargo runs.
697+
* An integer followed by "seconds", "minutes", "hours", "days", "weeks", or "months" --- Checks to delete old files at most the given time frame.
698+
660699
### `[http]`
661700

662701
The `[http]` table defines settings for HTTP behavior. This includes fetching

src/doc/src/reference/environment-variables.md

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -101,6 +101,7 @@ In summary, the supported environment variables are:
101101
* `CARGO_BUILD_DEP_INFO_BASEDIR` --- Dep-info relative directory, see [`build.dep-info-basedir`].
102102
* `CARGO_CARGO_NEW_VCS` --- The default source control system with [`cargo new`], see [`cargo-new.vcs`].
103103
* `CARGO_FUTURE_INCOMPAT_REPORT_FREQUENCY` --- How often we should generate a future incompat report notification, see [`future-incompat-report.frequency`].
104+
* `CARGO_GC_AUTO_FREQUENCY` --- Configures how often automatic garbage collection runs, see [`gc.auto.frequency`].
104105
* `CARGO_HTTP_DEBUG` --- Enables HTTP debugging, see [`http.debug`].
105106
* `CARGO_HTTP_PROXY` --- Enables HTTP proxy, see [`http.proxy`].
106107
* `CARGO_HTTP_TIMEOUT` --- The HTTP timeout, see [`http.timeout`].
@@ -167,6 +168,7 @@ In summary, the supported environment variables are:
167168
[`cargo-new.email`]: config.md#cargo-newemail
168169
[`cargo-new.vcs`]: config.md#cargo-newvcs
169170
[`future-incompat-report.frequency`]: config.md#future-incompat-reportfrequency
171+
[`gc.auto.frequency`]: config.md#gcautofrequency
170172
[`http.debug`]: config.md#httpdebug
171173
[`http.proxy`]: config.md#httpproxy
172174
[`http.timeout`]: config.md#httptimeout

src/doc/src/reference/unstable.md

Lines changed: 15 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -1465,36 +1465,18 @@ This will not affect any hard-coded paths in the source code, such as in strings
14651465

14661466
* Tracking Issue: [#12633](https://github.com/rust-lang/cargo/issues/12633)
14671467

1468-
The `-Zgc` flag enables garbage-collection within cargo's global cache within the cargo home directory.
1469-
This includes downloaded dependencies such as compressed `.crate` files, extracted `src` directories, registry index caches, and git dependencies.
1470-
When `-Zgc` is present, cargo will track the last time any index and dependency was used,
1471-
and then uses those timestamps to manually or automatically delete cache entries that have not been used for a while.
1472-
1473-
```sh
1474-
cargo build -Zgc
1475-
```
1476-
1477-
### Automatic garbage collection
1478-
1479-
Automatic deletion happens on commands that are already doing a significant amount of work,
1480-
such as all of the build commands (`cargo build`, `cargo test`, `cargo check`, etc.), and `cargo fetch`.
1481-
The deletion happens just after resolution and packages have been downloaded.
1482-
Automatic deletion is only done once per day (see `gc.auto.frequency` to configure).
1483-
Automatic deletion is disabled if cargo is offline such as with `--offline` or `--frozen` to avoid deleting artifacts that may need to be used if you are offline for a long period of time.
1468+
The `-Zgc` flag is used to enable certain features related to garbage-collection of cargo's global cache within the cargo home directory.
14841469

14851470
#### Automatic gc configuration
14861471

1487-
The automatic gc behavior can be specified via a cargo configuration setting.
1472+
The `-Zgc` flag will enable Cargo to read extra configuration options related to garbage collection.
14881473
The settings available are:
14891474

14901475
```toml
14911476
# Example config.toml file.
14921477

14931478
# This table defines the behavior for automatic garbage collection.
14941479
[gc.auto]
1495-
# The maximum frequency that automatic garbage collection happens.
1496-
# Can be "never" to disable automatic-gc, or "always" to run on every command.
1497-
frequency = "1 day"
14981480
# Anything older than this duration will be deleted in the source cache.
14991481
max-src-age = "1 month"
15001482
# Anything older than this duration will be deleted in the compressed crate cache.
@@ -1507,9 +1489,13 @@ max-git-co-age = "1 month"
15071489
max-git-db-age = "3 months"
15081490
```
15091491

1492+
Note that the [`gc.auto.frequency`] option was stabilized in Rust 1.82.
1493+
1494+
[`gc.auto.frequency`]: config.md#gcautofrequency
1495+
15101496
### Manual garbage collection with `cargo clean`
15111497

1512-
Manual deletion can be done with the `cargo clean gc` command.
1498+
Manual deletion can be done with the `cargo clean gc -Zgc` command.
15131499
Deletion of cache contents can be performed by passing one of the cache options:
15141500

15151501
- `--max-src-age=DURATION` --- Deletes source cache files that have not been used since the given age.
@@ -1528,9 +1514,9 @@ A DURATION is specified in the form "N seconds/minutes/days/weeks/months" where
15281514
A SIZE is specified in the form "N *suffix*" where *suffix* is B, kB, MB, GB, kiB, MiB, or GiB, and N is an integer or floating point number. If no suffix is specified, the number is the number of bytes.
15291515

15301516
```sh
1531-
cargo clean gc
1532-
cargo clean gc --max-download-age=1week
1533-
cargo clean gc --max-git-size=0 --max-download-size=100MB
1517+
cargo clean gc -Zgc
1518+
cargo clean gc -Zgc --max-download-age=1week
1519+
cargo clean gc -Zgc --max-git-size=0 --max-download-size=100MB
15341520
```
15351521

15361522
## open-namespaces
@@ -1814,3 +1800,8 @@ default behavior.
18141800

18151801
See the [build script documentation](build-scripts.md#rustc-check-cfg) for information
18161802
about specifying custom cfgs.
1803+
1804+
## Automatic garbage collection
1805+
1806+
Support for automatically deleting old files was stabilized in Rust 1.82.
1807+
More information can be found in the [config chapter](config.md#gcauto).

0 commit comments

Comments
 (0)