Support platforms without a timer

I've dabbled recently in seeing how hard it would be to compile rustfmt to wasm
and then run it in a web browser, and it turns out that it's [not too
hard][wasm]! In addition to patching a few dependencies which already have a
number of patches out rustfmt also needed some modifications to get it to work,
namely avoiding the usage of `Instant::now()` on the "happy path" which doesn't
work on wasm (it just panics).

This commit is an attempt to add a support for this by avoiding using
`Instant::now()` on the wasm target, but panicking if the actual time elapsed is
requested (which doesn't happen unless verbosely logging I believe).

[wasm]: https://alexcrichton.github.io/rustfmt-wasm/
This commit is contained in:
Alex Crichton 2018-09-09 11:12:13 -07:00
parent 6ada5b51cc
commit 46e2a2e7c7

View file

@ -64,7 +64,7 @@ fn format_project<T: FormatHandler>(
config: &Config, config: &Config,
handler: &mut T, handler: &mut T,
) -> Result<FormatReport, ErrorKind> { ) -> Result<FormatReport, ErrorKind> {
let mut timer = Timer::Initialized(Instant::now()); let mut timer = Timer::start();
let main_file = input.file_name(); let main_file = input.file_name();
let input_is_stdin = main_file == FileName::Stdin; let input_is_stdin = main_file == FileName::Stdin;
@ -344,14 +344,23 @@ pub(crate) struct ModifiedLines {
#[derive(Clone, Copy, Debug)] #[derive(Clone, Copy, Debug)]
enum Timer { enum Timer {
Disabled,
Initialized(Instant), Initialized(Instant),
DoneParsing(Instant, Instant), DoneParsing(Instant, Instant),
DoneFormatting(Instant, Instant, Instant), DoneFormatting(Instant, Instant, Instant),
} }
impl Timer { impl Timer {
fn start() -> Timer {
if cfg!(target_arch = "wasm32") {
Timer::Disabled
} else {
Timer::Initialized(Instant::now())
}
}
fn done_parsing(self) -> Self { fn done_parsing(self) -> Self {
match self { match self {
Timer::Disabled => Timer::Disabled,
Timer::Initialized(init_time) => Timer::DoneParsing(init_time, Instant::now()), Timer::Initialized(init_time) => Timer::DoneParsing(init_time, Instant::now()),
_ => panic!("Timer can only transition to DoneParsing from Initialized state"), _ => panic!("Timer can only transition to DoneParsing from Initialized state"),
} }
@ -359,6 +368,7 @@ impl Timer {
fn done_formatting(self) -> Self { fn done_formatting(self) -> Self {
match self { match self {
Timer::Disabled => Timer::Disabled,
Timer::DoneParsing(init_time, parse_time) => { Timer::DoneParsing(init_time, parse_time) => {
Timer::DoneFormatting(init_time, parse_time, Instant::now()) Timer::DoneFormatting(init_time, parse_time, Instant::now())
} }
@ -369,6 +379,7 @@ impl Timer {
/// Returns the time it took to parse the source files in seconds. /// Returns the time it took to parse the source files in seconds.
fn get_parse_time(&self) -> f32 { fn get_parse_time(&self) -> f32 {
match *self { match *self {
Timer::Disabled => panic!("this platform cannot time execution"),
Timer::DoneParsing(init, parse_time) | Timer::DoneFormatting(init, parse_time, _) => { Timer::DoneParsing(init, parse_time) | Timer::DoneFormatting(init, parse_time, _) => {
// This should never underflow since `Instant::now()` guarantees monotonicity. // This should never underflow since `Instant::now()` guarantees monotonicity.
Self::duration_to_f32(parse_time.duration_since(init)) Self::duration_to_f32(parse_time.duration_since(init))
@ -381,6 +392,7 @@ impl Timer {
/// not included. /// not included.
fn get_format_time(&self) -> f32 { fn get_format_time(&self) -> f32 {
match *self { match *self {
Timer::Disabled => panic!("this platform cannot time execution"),
Timer::DoneFormatting(_init, parse_time, format_time) => { Timer::DoneFormatting(_init, parse_time, format_time) => {
Self::duration_to_f32(format_time.duration_since(parse_time)) Self::duration_to_f32(format_time.duration_since(parse_time))
} }