diff --git a/CHANGELOG.md b/CHANGELOG.md index df4c674d32..be29986714 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -5,6 +5,11 @@ This project adheres to [Semantic Versioning](http://semver.org/). ## [Unreleased] +### Fixed + +- Soundness issue in the `MaybeUninit` implementation +- Warning for deprecated `mem::uninitialized` + ## [v0.4.3] - 2019-04-21 ### Changed diff --git a/README.md b/README.md index b8cbd00f7d..bf2ba83b9e 100644 --- a/README.md +++ b/README.md @@ -41,7 +41,7 @@ A concurrency framework for building real time systems. ## Requirements -- Rust 1.31.0+ +- Rust 1.36.0+ - Applications must be written using the 2018 edition. diff --git a/book/ru/src/README_RU.md b/book/ru/src/README_RU.md index 921837a928..cb5124e23a 100644 --- a/book/ru/src/README_RU.md +++ b/book/ru/src/README_RU.md @@ -39,7 +39,7 @@ ## Требования -- Rust 1.31.0+ +- Rust 1.36.0+ - Программы нужно писать используя 2018 edition. diff --git a/macros/src/codegen.rs b/macros/src/codegen.rs index ff8fb6508d..bf4a0fcfca 100644 --- a/macros/src/codegen.rs +++ b/macros/src/codegen.rs @@ -1948,13 +1948,13 @@ fn pre_init(ctxt: &Context, app: &App, analysis: &Analysis) -> proc_macro2::Toke // these are `MaybeUninit` arrays for task in ctxt.tasks.values() { let inputs = &task.inputs; - exprs.push(quote!(#inputs.write(core::mem::uninitialized());)) + exprs.push(quote!(#inputs.write(core::mem::MaybeUninit::uninit());)) } #[cfg(feature = "timer-queue")] for task in ctxt.tasks.values() { let scheduleds = &task.scheduleds; - exprs.push(quote!(#scheduleds.write(core::mem::uninitialized());)) + exprs.push(quote!(#scheduleds.write(core::mem::MaybeUninit::uninit());)) } // these are `MaybeUninit` `ReadyQueue`s diff --git a/src/export.rs b/src/export.rs index cf7293b620..e75d25ad2b 100644 --- a/src/export.rs +++ b/src/export.rs @@ -1,7 +1,5 @@ //! IMPLEMENTATION DETAILS. DO NOT USE ANYTHING IN THIS MODULE -#[cfg(not(feature = "nightly"))] -use core::ptr; use core::{cell::Cell, u8}; #[cfg(armv7m)] @@ -64,13 +62,11 @@ impl Priority { } } -#[cfg(feature = "nightly")] pub struct MaybeUninit { // we newtype so the end-user doesn't need `#![feature(maybe_uninit)]` in their code inner: core::mem::MaybeUninit, } -#[cfg(feature = "nightly")] impl MaybeUninit { pub const fn uninit() -> Self { MaybeUninit { @@ -86,61 +82,23 @@ impl MaybeUninit { self.inner.as_mut_ptr() } - pub fn write(&mut self, value: T) -> &mut T { - self.inner.write(value) - } -} - -#[cfg(not(feature = "nightly"))] -pub struct MaybeUninit { - value: Option, -} - -#[cfg(not(feature = "nightly"))] -const MSG: &str = - "you have hit a bug (UB) in RTFM implementation; try enabling this crate 'nightly' feature"; - -#[cfg(not(feature = "nightly"))] -impl MaybeUninit { - pub const fn uninit() -> Self { - MaybeUninit { value: None } - } - - pub fn as_ptr(&self) -> *const T { - if let Some(x) = self.value.as_ref() { - x - } else { - unreachable!(MSG) - } - } - - pub fn as_mut_ptr(&mut self) -> *mut T { - if let Some(x) = self.value.as_mut() { - x - } else { - unreachable!(MSG) - } - } - pub unsafe fn get_ref(&self) -> &T { - if let Some(x) = self.value.as_ref() { - x - } else { - unreachable!(MSG) - } + &*self.inner.as_ptr() } pub unsafe fn get_mut(&mut self) -> &mut T { - if let Some(x) = self.value.as_mut() { - x - } else { - unreachable!(MSG) - } + &mut *self.inner.as_mut_ptr() } - pub fn write(&mut self, val: T) { - // NOTE(volatile) we have observed UB when this uses a plain `ptr::write` - unsafe { ptr::write_volatile(&mut self.value, Some(val)) } + #[cfg(feature = "nightly")] + pub fn write(&mut self, value: T) -> &mut T { + self.inner.write(value) + } + + #[cfg(not(feature = "nightly"))] + pub fn write(&mut self, value: T) -> &mut T { + self.inner = core::mem::MaybeUninit::new(value); + unsafe { self.get_mut() } } } diff --git a/src/lib.rs b/src/lib.rs index b0bf6689e3..6471281a36 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -16,7 +16,7 @@ //! //! # Minimum Supported Rust Version (MSRV) //! -//! This crate is guaranteed to compile on stable Rust 1.31 (2018 edition) and up. It *might* +//! This crate is guaranteed to compile on stable Rust 1.36 (2018 edition) and up. It *might* //! compile on older versions but that may change in any new patch release. //! //! # Semantic Versioning @@ -41,7 +41,7 @@ //! usage, runtime overhead and initialization overhead. This feature requires a nightly compiler //! and may stop working at any time! -#![cfg_attr(feature = "nightly", feature(maybe_uninit))] +#![cfg_attr(feature = "nightly", feature(maybe_uninit_extra))] #![deny(missing_docs)] #![deny(warnings)] #![no_std]