Skip to content

Commit 0c8d59b

Browse files
Escape reserved characters on Windows from log path
1 parent 1c8a239 commit 0c8d59b

File tree

1 file changed

+38
-32
lines changed

1 file changed

+38
-32
lines changed

src/report/mod.rs

Lines changed: 38 additions & 32 deletions
Original file line numberDiff line numberDiff line change
@@ -28,11 +28,6 @@ url::define_encode_set! {
2828
pub REPORT_ENCODE_SET = [DEFAULT_ENCODE_SET] | { '+' }
2929
}
3030

31-
#[inline]
32-
fn url_encode(input: &str) -> String {
33-
utf8_percent_encode(input, REPORT_ENCODE_SET).to_string()
34-
}
35-
3631
#[derive(Serialize, Deserialize)]
3732
pub struct TestResults {
3833
pub crates: Vec<CrateResult>,
@@ -84,34 +79,44 @@ struct BuildTestResult {
8479
log: String,
8580
}
8681

87-
fn crate_to_path_fragment(toolchain: &Toolchain, krate: &Crate, encode: bool) -> PathBuf {
88-
let mut path = PathBuf::new();
89-
if encode {
90-
path.push(url_encode(&toolchain.to_string()));
91-
} else {
92-
path.push(toolchain.to_string());
82+
/// The type of sanitization required for a string.
83+
#[derive(Debug, Clone, Copy)]
84+
enum SanitizationContext {
85+
Url,
86+
Path,
87+
}
88+
89+
impl SanitizationContext {
90+
fn sanitize(self, input: &str) -> Cow<str> {
91+
match self {
92+
SanitizationContext::Url =>
93+
utf8_percent_encode(input, REPORT_ENCODE_SET).into(),
94+
95+
SanitizationContext::Path =>
96+
utf8_percent_encode(input, utils::fs::FILENAME_ENCODE_SET).into(),
97+
}
9398
}
99+
}
100+
101+
fn crate_to_path_fragment(toolchain: &Toolchain,
102+
krate: &Crate,
103+
dest: SanitizationContext) -> PathBuf
104+
{
105+
let mut path = PathBuf::new();
106+
path.push(dest.sanitize(&toolchain.to_string()).into_owned());
94107

95108
match *krate {
96109
Crate::Registry(ref details) => {
97110
path.push("reg");
98111

99112
let name = format!("{}-{}", details.name, details.version);
100-
if encode {
101-
path.push(url_encode(&name));
102-
} else {
103-
path.push(name);
104-
}
113+
path.push(dest.sanitize(&name).into_owned());
105114
}
106115
Crate::GitHub(ref repo) => {
107116
path.push("gh");
108117

109118
let name = format!("{}.{}", repo.org, repo.name);
110-
if encode {
111-
path.push(url_encode(&name));
112-
} else {
113-
path.push(name);
114-
}
119+
path.push(dest.sanitize(&name).into_owned());
115120
}
116121
Crate::Local(ref name) => {
117122
path.push("local");
@@ -141,10 +146,10 @@ pub fn generate_report<DB: ReadResults>(
141146

142147
Ok(BuildTestResult {
143148
res,
144-
log: crate_to_path_fragment(tc, &krate, true)
149+
log: crate_to_path_fragment(tc, &krate, SanitizationContext::Url)
145150
.to_str()
146151
.unwrap()
147-
.replace(r"\", "/"),
152+
.replace(r"\", "/"), // Normalize paths in reports generated on Windows
148153
})
149154
});
150155
// Convert errors to Nones
@@ -190,7 +195,8 @@ fn write_logs<DB: ReadResults, W: ReportWriter>(
190195
}
191196

192197
for tc in &ex.toolchains {
193-
let log_path = crate_to_path_fragment(tc, krate, false).join("log.txt");
198+
let log_path = crate_to_path_fragment(tc, krate, SanitizationContext::Path)
199+
.join("log.txt");
194200
let content = db
195201
.load_log(ex, tc, krate)
196202
.and_then(|c| c.ok_or_else(|| err_msg("missing logs")))
@@ -482,26 +488,26 @@ mod tests {
482488
org: "brson".into(),
483489
name: "hello-rs".into(),
484490
});
485-
let plus = Crate::Registry(RegistryCrate {
491+
let gt_plus = Crate::Registry(RegistryCrate {
486492
name: "foo".into(),
487-
version: "1.0+bar".into(),
493+
version: ">1.0+bar".into(),
488494
});
489495

490496
assert_eq!(
491-
crate_to_path_fragment(&MAIN_TOOLCHAIN, &reg, false),
497+
crate_to_path_fragment(&MAIN_TOOLCHAIN, &reg, SanitizationContext::Path),
492498
PathBuf::from("stable/reg/lazy_static-1.0")
493499
);
494500
assert_eq!(
495-
crate_to_path_fragment(&MAIN_TOOLCHAIN, &gh, false),
501+
crate_to_path_fragment(&MAIN_TOOLCHAIN, &gh, SanitizationContext::Path),
496502
PathBuf::from("stable/gh/brson.hello-rs")
497503
);
498504
assert_eq!(
499-
crate_to_path_fragment(&MAIN_TOOLCHAIN, &plus, false),
500-
PathBuf::from("stable/reg/foo-1.0+bar")
505+
crate_to_path_fragment(&MAIN_TOOLCHAIN, &gt_plus, SanitizationContext::Path),
506+
PathBuf::from("stable/reg/foo-%3E1.0+bar")
501507
);
502508
assert_eq!(
503-
crate_to_path_fragment(&MAIN_TOOLCHAIN, &plus, true),
504-
PathBuf::from("stable/reg/foo-1.0%2Bbar")
509+
crate_to_path_fragment(&MAIN_TOOLCHAIN, &gt_plus, SanitizationContext::Url),
510+
PathBuf::from("stable/reg/foo-%3E1.0%2Bbar")
505511
);
506512
}
507513

0 commit comments

Comments
 (0)