Skip to content

Commit a3a63c0

Browse files
committed
Fix #2229 detect available memory
This doesn't implement streaming IO for low memory situations - we still have the situation that low footprint situations will fail to install, but while it is the case that rustc's memory footprint is lower than our unpack footprint this is probably not urgent to fix, though I will get around to it. Being less aggressive about unpack buffer size though should reduce the number of support tickets from folk in these cases, I hope. We may end up getting tickets from folk with broken ulimit syscalls though, who knows.
1 parent d65e9de commit a3a63c0

File tree

8 files changed

+111
-45
lines changed

8 files changed

+111
-45
lines changed

Cargo.lock

Lines changed: 64 additions & 35 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

Cargo.toml

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -25,6 +25,7 @@ chrono = "0.4"
2525
clap = "2"
2626
download = { path = "download" }
2727
error-chain = "0.12"
28+
effective-limits = "0.3"
2829
flate2 = "1"
2930
git-testament = "0.1.4"
3031
home = "0.5"

src/dist/component/package.rs

Lines changed: 35 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -8,6 +8,7 @@ use crate::dist::component::transaction::*;
88
use crate::dist::temp;
99
use crate::errors::*;
1010
use crate::utils::notifications::Notification;
11+
use crate::utils::units;
1112
use crate::utils::utils;
1213

1314
use std::collections::{HashMap, HashSet};
@@ -17,7 +18,9 @@ use std::io::{self, ErrorKind as IOErrorKind, Read};
1718
use std::iter::FromIterator;
1819
use std::mem;
1920
use std::path::{Path, PathBuf};
21+
use std::sync::atomic::{AtomicBool, Ordering};
2022

23+
use lazy_static::lazy_static;
2124
use tar::EntryType;
2225

2326
/// The current metadata revision used by rust-installer
@@ -163,19 +166,40 @@ struct MemoryBudget {
163166
used: usize,
164167
}
165168

169+
lazy_static! {
170+
static ref RAM_NOTICE_SHOWN: AtomicBool = AtomicBool::new(false);
171+
}
172+
166173
// Probably this should live in diskio but ¯\_(ツ)_/¯
167174
impl MemoryBudget {
168-
fn new(max_file_size: usize) -> Self {
169-
const DEFAULT_UNPACK_RAM: usize = 400 * 1024 * 1024;
170-
let unpack_ram = if let Ok(budget_str) = env::var("RUSTUP_UNPACK_RAM") {
171-
if let Ok(budget) = budget_str.parse::<usize>() {
172-
budget
173-
} else {
174-
DEFAULT_UNPACK_RAM
175+
fn new(max_file_size: usize, effective_max_ram: usize) -> Self {
176+
const DEFAULT_UNPACK_RAM_MAX: usize = 500 * 1024 * 1024;
177+
const RAM_ALLOWANCE_FOR_RUSTUP_AND_BUFFERS: usize = 100 * 1024 * 1024;
178+
let ram_for_unpacking = effective_max_ram - RAM_ALLOWANCE_FOR_RUSTUP_AND_BUFFERS;
179+
let default_max_unpack_ram = std::cmp::min(DEFAULT_UNPACK_RAM_MAX, ram_for_unpacking);
180+
let unpack_ram = match env::var("RUSTUP_UNPACK_RAM")
181+
.ok()
182+
.and_then(|budget_str| budget_str.parse::<usize>().ok())
183+
{
184+
// Note: In future we may want to add a warning or even an override if a user
185+
// supplied budget is larger than effective_max_ram.
186+
Some(budget) => budget,
187+
None => {
188+
if RAM_NOTICE_SHOWN.load(Ordering::Acquire) {
189+
eprintln!(
190+
"Defaulting to {} unpack ram",
191+
units::Size::new(
192+
default_max_unpack_ram,
193+
units::Unit::B,
194+
units::UnitMode::Norm
195+
)
196+
);
197+
RAM_NOTICE_SHOWN.store(true, Ordering::Release);
198+
}
199+
default_max_unpack_ram
175200
}
176-
} else {
177-
DEFAULT_UNPACK_RAM
178201
};
202+
179203
if max_file_size > unpack_ram {
180204
panic!("RUSTUP_UNPACK_RAM must be larger than {}", max_file_size);
181205
}
@@ -278,7 +302,8 @@ fn unpack_without_first_dir<'a, R: Read>(
278302
.entries()
279303
.chain_err(|| ErrorKind::ExtractingPackage)?;
280304
const MAX_FILE_SIZE: u64 = 200_000_000;
281-
let mut budget = MemoryBudget::new(MAX_FILE_SIZE as usize);
305+
let effective_max_ram = effective_limits::memory_limit()?;
306+
let mut budget = MemoryBudget::new(MAX_FILE_SIZE as usize, effective_max_ram as usize);
282307

283308
let mut directories: HashMap<PathBuf, DirStatus> = HashMap::new();
284309
// Path is presumed to exist. Call it a precondition.

src/errors.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,7 @@ pub const TOOLSTATE_MSG: &str =
2222
error_chain! {
2323
links {
2424
Download(download::Error, download::ErrorKind);
25+
Limits(effective_limits::Error, effective_limits::ErrorKind);
2526
}
2627

2728
foreign_links {

tests/cli-exact.rs

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -38,6 +38,7 @@ info: downloading component 'rust-docs'
3838
info: downloading component 'rust-std'
3939
info: downloading component 'rustc'
4040
info: installing component 'cargo'
41+
Defaulting to 500.0 MiB unpack ram
4142
info: installing component 'rust-docs'
4243
info: installing component 'rust-std'
4344
info: installing component 'rustc'
@@ -172,6 +173,7 @@ info: downloading component 'rust-docs'
172173
info: downloading component 'rust-std'
173174
info: downloading component 'rustc'
174175
info: installing component 'cargo'
176+
Defaulting to 500.0 MiB unpack ram
175177
info: installing component 'rust-docs'
176178
info: installing component 'rust-std'
177179
info: installing component 'rustc'
@@ -504,6 +506,7 @@ fn cross_install_indicates_target() {
504506
&format!(
505507
r"info: downloading component 'rust-std' for '{0}'
506508
info: installing component 'rust-std' for '{0}'
509+
Defaulting to 500.0 MiB unpack ram
507510
",
508511
clitools::CROSS_ARCH1
509512
),

tests/cli-rustup.rs

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -56,6 +56,7 @@ info: removing previous version of component 'rust-docs'
5656
info: removing previous version of component 'rust-std'
5757
info: removing previous version of component 'rustc'
5858
info: installing component 'cargo'
59+
Defaulting to 500.0 MiB unpack ram
5960
info: installing component 'rust-docs'
6061
info: installing component 'rust-std'
6162
info: installing component 'rustc'
@@ -96,6 +97,7 @@ info: removing previous version of component 'rust-docs'
9697
info: removing previous version of component 'rust-std'
9798
info: removing previous version of component 'rustc'
9899
info: installing component 'cargo'
100+
Defaulting to 500.0 MiB unpack ram
99101
info: installing component 'rust-docs'
100102
info: installing component 'rust-std'
101103
info: installing component 'rustc'
@@ -160,6 +162,7 @@ info: removing previous version of component 'rust-docs'
160162
info: removing previous version of component 'rust-std'
161163
info: removing previous version of component 'rustc'
162164
info: installing component 'cargo'
165+
Defaulting to 500.0 MiB unpack ram
163166
info: installing component 'rust-docs'
164167
info: installing component 'rust-std'
165168
info: installing component 'rustc'
@@ -230,6 +233,7 @@ info: removing previous version of component 'rust-docs'
230233
info: removing previous version of component 'rust-std'
231234
info: removing previous version of component 'rustc'
232235
info: installing component 'cargo'
236+
Defaulting to 500.0 MiB unpack ram
233237
info: installing component 'rust-docs'
234238
info: installing component 'rust-std'
235239
info: installing component 'rustc'
@@ -291,6 +295,7 @@ info: downloading component 'rust-docs'
291295
info: downloading component 'rust-std'
292296
info: downloading component 'rustc'
293297
info: installing component 'cargo'
298+
Defaulting to 500.0 MiB unpack ram
294299
info: installing component 'rust-docs'
295300
info: installing component 'rust-std'
296301
info: installing component 'rustc'

tests/cli-self-upd.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -883,6 +883,7 @@ info: downloading component 'rust-docs'
883883
info: downloading component 'rust-std'
884884
info: downloading component 'rustc'
885885
info: installing component 'cargo'
886+
Defaulting to 500.0 MiB unpack ram
886887
info: installing component 'rust-docs'
887888
info: installing component 'rust-std'
888889
info: installing component 'rustc'

tests/cli-v2.rs

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1342,6 +1342,7 @@ info: downloading component 'cargo'
13421342
info: downloading component 'rust-docs'
13431343
info: downloading component 'rustc'
13441344
info: installing component 'cargo'
1345+
Defaulting to 500.0 MiB unpack ram
13451346
info: installing component 'rust-docs'
13461347
info: installing component 'rustc'
13471348
"

0 commit comments

Comments
 (0)