diff -Nru rust-cast-0.2.2/build.rs rust-cast-0.2.3/build.rs --- rust-cast-0.2.2/build.rs 1970-01-01 00:00:00.000000000 +0000 +++ rust-cast-0.2.3/build.rs 2019-11-16 23:43:56.000000000 +0000 @@ -0,0 +1,8 @@ +extern crate rustc_version; + +fn main() { + let vers = rustc_version::version().unwrap(); + if vers.major == 1 && vers.minor >= 26 { + println!("cargo:rustc-cfg=stable_i128") + } +} diff -Nru rust-cast-0.2.2/Cargo.toml rust-cast-0.2.3/Cargo.toml --- rust-cast-0.2.2/Cargo.toml 2017-05-07 21:55:45.000000000 +0000 +++ rust-cast-0.2.3/Cargo.toml 1970-01-01 00:00:00.000000000 +0000 @@ -3,7 +3,7 @@ # When uploading crates to the registry Cargo will automatically # "normalize" Cargo.toml files for maximal compatibility # with all versions of Cargo and also rewrite `path` dependencies -# to registry (e.g. crates.io) dependencies +# to registry (e.g., crates.io) dependencies # # If you believe there's an error in this file please file an # issue against the rust-lang/cargo repository. If you're @@ -12,15 +12,18 @@ [package] name = "cast" -version = "0.2.2" +version = "0.2.3" authors = ["Jorge Aparicio "] +build = "build.rs" description = "Ergonomic, checked cast functions for primitive types" documentation = "https://docs.rs/cast" keywords = ["checked", "cast", "primitive", "integer", "float"] license = "MIT OR Apache-2.0" repository = "https://github.com/japaric/cast.rs" [dev-dependencies.quickcheck] -version = "0.4.1" +version = "0.9.0" +[build-dependencies.rustc_version] +version = "0.2.3" [features] default = ["std"] diff -Nru rust-cast-0.2.2/Cargo.toml.orig rust-cast-0.2.3/Cargo.toml.orig --- rust-cast-0.2.2/Cargo.toml.orig 2017-05-07 21:55:45.000000000 +0000 +++ rust-cast-0.2.3/Cargo.toml.orig 2019-11-16 23:43:56.000000000 +0000 @@ -1,12 +1,13 @@ [package] authors = ["Jorge Aparicio "] +build = "build.rs" description = "Ergonomic, checked cast functions for primitive types" documentation = "https://docs.rs/cast" keywords = ["checked", "cast", "primitive", "integer", "float"] license = "MIT OR Apache-2.0" name = "cast" repository = "https://github.com/japaric/cast.rs" -version = "0.2.2" +version = "0.2.3" [features] # Assume we should use `std` unless asked to do otherwise. @@ -17,5 +18,8 @@ # Enable this for i128/u128 support x128 = [] +[build-dependencies] +rustc_version = "0.2.3" + [dev-dependencies] -quickcheck = "0.4.1" +quickcheck = "0.9.0" diff -Nru rust-cast-0.2.2/.cargo_vcs_info.json rust-cast-0.2.3/.cargo_vcs_info.json --- rust-cast-0.2.2/.cargo_vcs_info.json 1970-01-01 00:00:00.000000000 +0000 +++ rust-cast-0.2.3/.cargo_vcs_info.json 1970-01-01 00:00:00.000000000 +0000 @@ -0,0 +1,5 @@ +{ + "git": { + "sha1": "74cec5dcf2014ecfe7cb05837b147cbb4f49024e" + } +} diff -Nru rust-cast-0.2.2/CHANGELOG.md rust-cast-0.2.3/CHANGELOG.md --- rust-cast-0.2.2/CHANGELOG.md 2017-05-07 21:55:41.000000000 +0000 +++ rust-cast-0.2.3/CHANGELOG.md 2019-11-16 23:43:56.000000000 +0000 @@ -7,6 +7,17 @@ ## [Unreleased] +## [v0.2.3] - 2018-11-17 + +### Changed + +- Documented the guaranteed MRSV to be 1.13 +- The `x128` feature now works on *stable* Rust 1.26+ + +### Fixed + +- Overflow and underflow checks when casting a float to an unsigned integer + ## [v0.2.2] - 2017-05-07 ### Fixed @@ -36,7 +47,8 @@ Initial release -[Unreleased]: https://github.com/japaric/cast.rs/compare/v0.2.2...HEAD +[Unreleased]: https://github.com/japaric/cast.rs/compare/v0.2.3...HEAD +[v0.2.3]: https://github.com/japaric/cast.rs/compare/v0.2.2...v0.2.3 [v0.2.2]: https://github.com/japaric/cast.rs/compare/v0.2.1...v0.2.2 [v0.2.1]: https://github.com/japaric/cast.rs/compare/v0.2.0...v0.2.1 [v0.2.0]: https://github.com/japaric/cast.rs/compare/v0.1.0...v0.2.0 diff -Nru rust-cast-0.2.2/ci/install.sh rust-cast-0.2.3/ci/install.sh --- rust-cast-0.2.2/ci/install.sh 2017-02-09 01:03:24.000000000 +0000 +++ rust-cast-0.2.3/ci/install.sh 2019-11-16 23:43:56.000000000 +0000 @@ -1,21 +1,9 @@ -set -ex +set -euxo pipefail main() { - curl https://sh.rustup.rs -sSf | \ - sh -s -- -y --default-toolchain $TRAVIS_RUST_VERSION - - local latest=$(git ls-remote --tags --refs --exit-code https://github.com/japaric/cross \ - | cut -d/ -f3 \ - | grep -E '^v[0-9.]+$' \ - | sort --version-sort \ - | tail -n1) - - curl -LSfs https://japaric.github.io/trust/install.sh | \ - sh -s -- \ - --force \ - --git japaric/cross \ - --tag $latest \ - --target x86_64-unknown-linux-gnu + if [ $TARGET != x86_64-unknown-linux-gnu ]; then + rustup target add $TARGET + fi } main diff -Nru rust-cast-0.2.2/ci/script.sh rust-cast-0.2.3/ci/script.sh --- rust-cast-0.2.2/ci/script.sh 2017-05-06 13:56:54.000000000 +0000 +++ rust-cast-0.2.3/ci/script.sh 2019-11-16 23:43:56.000000000 +0000 @@ -1,14 +1,43 @@ -set -ex +set -euxo pipefail main() { - cross test --target $TARGET - cross test --target $TARGET --release + # not MSRV + if [ $TRAVIS_RUST_VERSION != 1.13.0 ]; then + cargo check --target $TARGET --no-default-features - [ "$TRAVIS_RUST_VERSION" -eq "nightly" ] && cross test --feature x128 --target $TARGET - [ "$TRAVIS_RUST_VERSION" -eq "nightly" ] && cross test --feature x128 --target $TARGET --release - - cross test --no-default-features --target $TARGET - cross test --no-default-features --target $TARGET --release + cargo test --features x128 --target $TARGET + cargo test --features x128 --target $TARGET --release + else + cargo build --target $TARGET --no-default-features + cargo build --target $TARGET + fi } +# fake Travis variables to be able to run this on a local machine +if [ -z ${TRAVIS_BRANCH-} ]; then + TRAVIS_BRANCH=staging +fi + +if [ -z ${TRAVIS_PULL_REQUEST-} ]; then + TRAVIS_PULL_REQUEST=false +fi + +if [ -z ${TRAVIS_RUST_VERSION-} ]; then + case $(rustc -V) in + *nightly*) + TRAVIS_RUST_VERSION=nightly + ;; + *beta*) + TRAVIS_RUST_VERSION=beta + ;; + *) + TRAVIS_RUST_VERSION=stable + ;; + esac +fi + +if [ -z ${TARGET-} ]; then + TARGET=$(rustc -Vv | grep host | cut -d ' ' -f2) +fi + main diff -Nru rust-cast-0.2.2/debian/cargo-checksum.json rust-cast-0.2.3/debian/cargo-checksum.json --- rust-cast-0.2.2/debian/cargo-checksum.json 2019-08-06 16:19:46.000000000 +0000 +++ rust-cast-0.2.3/debian/cargo-checksum.json 2019-12-01 09:10:24.000000000 +0000 @@ -1 +1 @@ -{"package":"926013f2860c46252efceabb19f4a6b308197505082c609025aa6706c011d427","files":{}} +{"package":"4b9434b9a5aa1450faa3f9cb14ea0e8c53bb5d2b3c1bfd1ab4fc03e9f33fbfb0","files":{}} diff -Nru rust-cast-0.2.2/debian/changelog rust-cast-0.2.3/debian/changelog --- rust-cast-0.2.2/debian/changelog 2019-08-06 16:19:46.000000000 +0000 +++ rust-cast-0.2.3/debian/changelog 2019-12-01 09:10:24.000000000 +0000 @@ -1,3 +1,9 @@ +rust-cast (0.2.3-1) unstable; urgency=medium + + * Package cast 0.2.3 from crates.io using debcargo 2.4.0 + + -- Sylvestre Ledru Sun, 01 Dec 2019 10:10:24 +0100 + rust-cast (0.2.2-2) unstable; urgency=medium * Package cast 0.2.2 from crates.io using debcargo 2.2.10 diff -Nru rust-cast-0.2.2/debian/control rust-cast-0.2.3/debian/control --- rust-cast-0.2.2/debian/control 2019-08-06 16:19:46.000000000 +0000 +++ rust-cast-0.2.3/debian/control 2019-12-01 09:10:24.000000000 +0000 @@ -2,10 +2,11 @@ Section: rust Priority: optional Build-Depends: debhelper (>= 11), - dh-cargo (>= 15), + dh-cargo (>= 18), cargo:native , rustc:native , - libstd-rust-dev + libstd-rust-dev , + librust-rustc-version-0.2+default-dev (>= 0.2.3-~~) Maintainer: Debian Rust Maintainers Uploaders: Sylvestre Ledru @@ -17,7 +18,8 @@ Architecture: any Multi-Arch: same Depends: - ${misc:Depends} + ${misc:Depends}, + librust-rustc-version-0.2+default-dev (>= 0.2.3-~~) Provides: librust-cast+default-dev (= ${binary:Version}), librust-cast+std-dev (= ${binary:Version}), @@ -30,10 +32,10 @@ librust-cast-0.2+default-dev (= ${binary:Version}), librust-cast-0.2+std-dev (= ${binary:Version}), librust-cast-0.2+x128-dev (= ${binary:Version}), - librust-cast-0.2.2-dev (= ${binary:Version}), - librust-cast-0.2.2+default-dev (= ${binary:Version}), - librust-cast-0.2.2+std-dev (= ${binary:Version}), - librust-cast-0.2.2+x128-dev (= ${binary:Version}) + librust-cast-0.2.3-dev (= ${binary:Version}), + librust-cast-0.2.3+default-dev (= ${binary:Version}), + librust-cast-0.2.3+std-dev (= ${binary:Version}), + librust-cast-0.2.3+x128-dev (= ${binary:Version}) Description: Ergonomic, checked cast functions for primitive types - Rust source code This package contains the source for the Rust cast crate, packaged by debcargo for use with cargo and dh-cargo. diff -Nru rust-cast-0.2.2/debian/tests/control rust-cast-0.2.3/debian/tests/control --- rust-cast-0.2.2/debian/tests/control 1970-01-01 00:00:00.000000000 +0000 +++ rust-cast-0.2.3/debian/tests/control 2019-12-01 09:10:24.000000000 +0000 @@ -0,0 +1,7 @@ +Test-Command: /usr/share/cargo/bin/cargo-auto-test cast 0.2.3 --all-targets --all-features +Depends: dh-cargo (>= 18), librust-quickcheck-0.9+default-dev, @ +Restrictions: allow-stderr, skip-not-installable + +Test-Command: /usr/share/cargo/bin/cargo-auto-test cast 0.2.3 --all-targets --no-default-features +Depends: dh-cargo (>= 18), librust-quickcheck-0.9+default-dev, librust-cast-dev +Restrictions: allow-stderr, skip-not-installable diff -Nru rust-cast-0.2.2/src/lib.rs rust-cast-0.2.3/src/lib.rs --- rust-cast-0.2.2/src/lib.rs 2017-05-07 21:54:29.000000000 +0000 +++ rust-cast-0.2.3/src/lib.rs 2019-11-16 23:43:56.000000000 +0000 @@ -81,6 +81,11 @@ //! # } //! ``` //! +//! ## Minimal Supported Rust Version +//! +//! This crate is guaranteed to compile on stable Rust 1.13 and up. It *might* compile on older +//! versions but that may change in any new patch release. +//! //! ## Building without `std` //! //! This crate can be used without Rust's `std` crate by declaring it as @@ -93,10 +98,8 @@ #![deny(missing_docs)] #![deny(warnings)] #![allow(const_err)] - #![cfg_attr(not(feature = "std"), no_std)] - -#![cfg_attr(feature = "x128", feature(i128_type, i128))] +#![cfg_attr(all(feature = "x128", not(stable_i128)), feature(i128_type, i128))] #[cfg(feature = "std")] extern crate core; @@ -106,7 +109,7 @@ extern crate quickcheck; use core::fmt; -#[cfg(feature="std")] +#[cfg(feature = "std")] use std::error; #[cfg(test)] @@ -146,7 +149,7 @@ } } -#[cfg(feature="std")] +#[cfg(feature = "std")] impl error::Error for Error { fn description(&self) -> &str { self.description_helper() @@ -273,7 +276,7 @@ /// From a float `$src` to an integer `$dst` macro_rules! from_float { - ($($src:ident => $($dst:ident),+);+;) => { + ($($src:ident, $usrc:ident => $($dst:ident),+);+;) => { $( $( impl From<$src> for $dst { @@ -288,11 +291,29 @@ } else if src == $src::INFINITY || src == $src::NEG_INFINITY { Error::Infinite + } else if { + // we subtract 1 ULP (unit of least precision) here because some + // lossy conversions like `u64::MAX as f64` round *up* and we want + // to avoid this evaluating to false in that case + use core::mem::transmute; + let max = unsafe { + transmute::<_, $src>(transmute::<_, $usrc>($dst::MAX as $src) - 1) + }; + src > max + } { + Error::Overflow + } else if $dst::MIN == 0 { + // when casting to unsigned integer, negative values close to 0 but + // larger than 1.0 should be truncated to 0; this behavior matches + // casting from a float to a signed integer + if src <= -1.0 { + Error::Underflow + } else { + return Ok(src as $dst); + } } else if src < $dst::MIN as $src { Error::Underflow - } else if src > $dst::MAX as $src { - Error::Overflow - } else { + } else { return Ok(src as $dst); }) } @@ -304,12 +325,13 @@ /// From a float `$src` to an integer `$dst`, where $dst is large enough to contain /// all values of `$src`. We can't ever overflow here +#[cfg(feature = "x128")] macro_rules! from_float_dst { ($($src:ident => $($dst:ident),+);+;) => { $( $( impl From<$src> for $dst { - type Output = Result<$dst, Error>; + type Output = Result<$dst, Error>; #[inline] #[allow(unused_comparisons)] @@ -321,7 +343,7 @@ } else if src == $src::INFINITY || src == $src::NEG_INFINITY { Error::Infinite - } else if ($dst::MIN == 0) && src < 0.0 { + } else if ($dst::MIN == 0) && src <= -1.0 { Error::Underflow } else { return Ok(src as $dst); @@ -388,8 +410,8 @@ } from_float! { - f32 => i8, i16, i32, isize, i64, u8, u16, u32, usize, u64; - f64 => i8, i16, i32, isize, i64, u8, u16, u32, usize, u64; + f32, u32 => i8, i16, i32, isize, i64, u8, u16, u32, usize, u64; + f64, u64 => i8, i16, i32, isize, i64, u8, u16, u32, usize, u64; } } @@ -446,8 +468,8 @@ } from_float! { - f32 => i8, i16, i32, i64, isize, u8, u16, u32, u64, usize; - f64 => i8, i16, i32, i64, isize, u8, u16, u32, u64, usize; + f32, u32 => i8, i16, i32, i64, isize, u8, u16, u32, u64, usize; + f64, u64 => i8, i16, i32, i64, isize, u8, u16, u32, u64, usize; } } @@ -494,11 +516,12 @@ // Float from_float! { - f32 => i128; - f64 => i128, u128; + f32, u32 => i128; + f64, u64 => i128, u128; } + from_float_dst! { - f32 => u128; + f32 => u128; } } diff -Nru rust-cast-0.2.2/src/test.rs rust-cast-0.2.3/src/test.rs --- rust-cast-0.2.2/src/test.rs 2017-05-07 21:54:29.000000000 +0000 +++ rust-cast-0.2.3/src/test.rs 2019-11-16 23:43:56.000000000 +0000 @@ -189,3 +189,33 @@ use u128; assert_eq!(u128(42.0f32), Ok(42)); } + +#[test] +fn gh16() { + assert_eq!(super::u64(-0.01_f64), Ok(0)); + assert_eq!(super::u64(-0.99_f32), Ok(0)); + + assert_eq!(super::u32(-0.99_f64), Ok(0)); + assert_eq!(super::u32(-0.01_f32), Ok(0)); + + assert_eq!(super::u64(0.01_f64), Ok(0)); + assert_eq!(super::u64(0.99_f32), Ok(0)); + + assert_eq!(super::u32(0.99_f64), Ok(0)); + assert_eq!(super::u32(0.01_f32), Ok(0)); +} + +#[test] +fn gh15() { + assert_eq!(super::u32(32_f32.exp2()), Err(super::Error::Overflow)); + assert_eq!(super::u32(32_f64.exp2()), Err(super::Error::Overflow)); + + assert_eq!(super::u64(64_f32.exp2()), Err(super::Error::Overflow)); + assert_eq!(super::u64(64_f64.exp2()), Err(super::Error::Overflow)); + + assert_eq!(super::u8(8_f32.exp2()), Err(super::Error::Overflow)); + assert_eq!(super::u8(8_f64.exp2()), Err(super::Error::Overflow)); + + assert_eq!(super::u16(16_f32.exp2()), Err(super::Error::Overflow)); + assert_eq!(super::u16(16_f64.exp2()), Err(super::Error::Overflow)); +} diff -Nru rust-cast-0.2.2/.travis.yml rust-cast-0.2.3/.travis.yml --- rust-cast-0.2.2/.travis.yml 2017-05-06 13:43:17.000000000 +0000 +++ rust-cast-0.2.3/.travis.yml 2019-11-16 23:43:56.000000000 +0000 @@ -1,28 +1,19 @@ -dist: trusty language: rust -services: docker -sudo: required -rust: stable - -env: TARGET=x86_64-unknown-linux-gnu matrix: include: - - env: TARGET=i686-unknown-linux-gnu + # MSRV - env: TARGET=x86_64-unknown-linux-gnu - rust: beta - - env: TARGET=i686-unknown-linux-gnu - rust: beta + rust: 1.13.0 + + # 32-bit + - env: TARGET=i686-unknown-linux-musl - env: TARGET=x86_64-unknown-linux-gnu - rust: nightly - - env: TARGET=i686-unknown-linux-gnu - rust: nightly before_install: set -e install: - - sh ci/install.sh - - source ~/.cargo/env || true + - bash ci/install.sh script: - bash ci/script.sh @@ -30,13 +21,14 @@ after_script: set +e cache: cargo + before_cache: - chmod -R a+r $HOME/.cargo branches: only: - - auto - - try + - staging + - trying notifications: email: