diff options
| author | kennytm <kennytm@gmail.com> | 2017-09-01 01:16:24 +0800 |
|---|---|---|
| committer | kennytm <kennytm@gmail.com> | 2017-09-07 17:14:27 +0800 |
| commit | 8410ca663258423cd16b0741f7a053b320e13da0 (patch) | |
| tree | 97c6f21fe2697ee48960c6b4d3126914370c1684 /src/libstd/sys/unix/time.rs | |
| parent | a6a9d4c5fd214cb8110482dee2017607e23ccc7b (diff) | |
| download | rust-8410ca663258423cd16b0741f7a053b320e13da0.tar.gz rust-8410ca663258423cd16b0741f7a053b320e13da0.zip | |
Properly detect overflow in Instance +/- Duration.
Avoid unchecked cast from `u64` to `i64`. Use `try_into()` for checked cast. (On Unix, cast to `time_t` instead of `i64`.)
Diffstat (limited to 'src/libstd/sys/unix/time.rs')
| -rw-r--r-- | src/libstd/sys/unix/time.rs | 22 |
1 files changed, 15 insertions, 7 deletions
diff --git a/src/libstd/sys/unix/time.rs b/src/libstd/sys/unix/time.rs index a1ad94872de..c1bea95ce91 100644 --- a/src/libstd/sys/unix/time.rs +++ b/src/libstd/sys/unix/time.rs @@ -13,6 +13,7 @@ use libc; use time::Duration; pub use self::inner::{Instant, SystemTime, UNIX_EPOCH}; +use convert::TryInto; const NSEC_PER_SEC: u64 = 1_000_000_000; @@ -41,8 +42,12 @@ impl Timespec { } fn add_duration(&self, other: &Duration) -> Timespec { - let secs = (self.t.tv_sec as i64).checked_add(other.as_secs() as i64); - let mut secs = secs.expect("overflow when adding duration to time"); + let mut secs = other + .as_secs() + .try_into() // <- target type would be `libc::time_t` + .ok() + .and_then(|secs| self.t.tv_sec.checked_add(secs)) + .expect("overflow when adding duration to time"); // Nano calculations can't overflow because nanos are <1B which fit // in a u32. @@ -54,16 +59,19 @@ impl Timespec { } Timespec { t: libc::timespec { - tv_sec: secs as libc::time_t, + tv_sec: secs, tv_nsec: nsec as libc::c_long, }, } } fn sub_duration(&self, other: &Duration) -> Timespec { - let secs = (self.t.tv_sec as i64).checked_sub(other.as_secs() as i64); - let mut secs = secs.expect("overflow when subtracting duration \ - from time"); + let mut secs = other + .as_secs() + .try_into() // <- target type would be `libc::time_t` + .ok() + .and_then(|secs| self.t.tv_sec.checked_sub(secs)) + .expect("overflow when subtracting duration from time"); // Similar to above, nanos can't overflow. let mut nsec = self.t.tv_nsec as i32 - other.subsec_nanos() as i32; @@ -74,7 +82,7 @@ impl Timespec { } Timespec { t: libc::timespec { - tv_sec: secs as libc::time_t, + tv_sec: secs, tv_nsec: nsec as libc::c_long, }, } |
