diff --git a/examples/blinky.rs b/examples/blinky.rs
index c0e5592adbaafe0956dd126355743c16fc5ab576..b911a9ad1542decc27396096cf2a5930b1cf0e61 100644
--- a/examples/blinky.rs
+++ b/examples/blinky.rs
@@ -1,59 +1,57 @@
 //! Turns the user LED on
 
-#![feature(const_fn)]
-#![feature(used)]
+#![deny(warnings)]
+#![feature(plugin)]
 #![no_std]
+#![plugin(cortex_m_rtfm_macros)]
 
 extern crate blue_pill;
 
-extern crate embedded_hal as hal;
-
-// version = "0.2.3"
-extern crate cortex_m_rt;
-
-// version = "0.1.0"
-#[macro_use]
+#[macro_use(task)]
 extern crate cortex_m_rtfm as rtfm;
 
 use blue_pill::Timer;
 use blue_pill::led::{self, Green};
-use blue_pill::stm32f103xx;
+use blue_pill::prelude::*;
 use blue_pill::time::Hertz;
-use hal::prelude::*;
-use rtfm::{Local, P0, P1, T0, T1, TMax};
-use stm32f103xx::interrupt::TIM1_UP_TIM10;
+use rtfm::Threshold;
 
-// CONFIGURATION
-const FREQUENCY: Hertz = Hertz(1);
+rtfm! {
+    device: blue_pill::stm32f103xx,
+
+    resources: {},
 
-// RESOURCES
-peripherals!(stm32f103xx, {
-    GPIOC: Peripheral {
-        ceiling: C0,
+    init: {
+        path: init,
     },
-    RCC: Peripheral {
-        ceiling: C0,
+
+    idle: {
+        path: idle,
     },
-    TIM1: Peripheral {
-        ceiling: C1,
+
+    tasks: {
+        TIM2: {
+            priority: 1,
+            enabled: true,
+            resources: [TIM2],
+        },
     },
-});
+}
 
-// INITIALIZATION PHASE
-fn init(ref prio: P0, thr: &TMax) {
-    let gpioc = &GPIOC.access(prio, thr);
-    let rcc = &RCC.access(prio, thr);
-    let tim1 = TIM1.access(prio, thr);
+// CONFIGURATION
+const FREQUENCY: Hertz = Hertz(1);
 
-    let timer = Timer(&*tim1);
+// INITIALIZATION PHASE
+fn init(p: init::Peripherals) {
+    let timer = Timer(p.TIM2);
 
-    led::init(gpioc, rcc);
-    timer.init(FREQUENCY.invert(), rcc);
+    led::init(p.GPIOC, p.RCC);
+    timer.init(FREQUENCY.invert(), p.RCC);
     timer.resume();
 }
 
 // IDLE LOOP
-fn idle(_prio: P0, _thr: T0) -> ! {
+fn idle() -> ! {
     // Sleep
     loop {
         rtfm::wfi();
@@ -61,29 +59,18 @@ fn idle(_prio: P0, _thr: T0) -> ! {
 }
 
 // TASKS
-tasks!(stm32f103xx, {
-    blink: Task {
-        interrupt: TIM1_UP_TIM10,
-        priority: P1,
-        enabled: true,
-    },
+task!(TIM2, blink, Local {
+    state: bool = false;
 });
 
-fn blink(mut task: TIM1_UP_TIM10, ref prio: P1, ref thr: T1) {
-    static STATE: Local<bool, TIM1_UP_TIM10> = Local::new(false);
-
-    let tim1 = TIM1.access(prio, thr);
+fn blink(_t: Threshold, l: &mut Local, r: TIM2::Resources) {
+    let timer = Timer(r.TIM2);
 
-    let timer = Timer(&*tim1);
-
-    // NOTE(wait) timeout should have already occurred
     timer.wait().unwrap();
 
-    let state = STATE.borrow_mut(&mut task);
-
-    *state = !*state;
+    l.state = !l.state;
 
-    if *state {
+    if l.state {
         Green.on();
     } else {
         Green.off();
diff --git a/examples/capture1.rs b/examples/capture1.rs
index 6cd39ecb9011bf428ecc96c53a8a84835f7cdefe..5f9cc8bc7f9f7025848cbb981943ad8a95cea62c 100644
--- a/examples/capture1.rs
+++ b/examples/capture1.rs
@@ -1,75 +1,47 @@
 //! Input capture using TIM1
 
 #![deny(warnings)]
-#![feature(const_fn)]
-#![feature(used)]
+#![feature(plugin)]
 #![no_std]
+#![plugin(cortex_m_rtfm_macros)]
 
 extern crate blue_pill;
-
-#[macro_use]
+#[macro_use(iprint, iprintln)]
 extern crate cortex_m;
-
-extern crate embedded_hal as hal;
-
-// version = "0.2.3"
-extern crate cortex_m_rt;
-
-// version = "0.1.0"
-#[macro_use]
 extern crate cortex_m_rtfm as rtfm;
-
 extern crate nb;
 
-use blue_pill::stm32f103xx;
+use blue_pill::prelude::*;
 use blue_pill::time::Milliseconds;
 use blue_pill::{Capture, Channel};
-use hal::prelude::*;
-use rtfm::{P0, T0, TMax};
 
 // CONFIGURATION
 const RESOLUTION: Milliseconds = Milliseconds(1);
 
-// RESOURCES
-peripherals!(stm32f103xx, {
-    AFIO: Peripheral {
-        ceiling: C0,
-    },
-    GPIOA: Peripheral {
-        ceiling: C0,
-    },
-    ITM: Peripheral {
-        ceiling: C0,
-    },
-    RCC: Peripheral {
-        ceiling: C0,
-    },
-    TIM1: Peripheral {
-        ceiling: C0,
+rtfm! {
+    device: blue_pill::stm32f103xx,
+
+    init: {
+        path: init,
     },
-});
 
-// INITIALIZATION PHASE
-fn init(ref prio: P0, thr: &TMax) {
-    let afio = &AFIO.access(prio, thr);
-    let gpioa = &GPIOA.access(prio, thr);
-    let rcc = &RCC.access(prio, thr);
-    let tim1 = TIM1.access(prio, thr);
+    idle: {
+        path: idle,
+        resources: [ITM, TIM1],
+    },
+}
 
-    let capture = Capture(&*tim1);
+fn init(p: init::Peripherals) {
+    let capture = Capture(p.TIM1);
 
-    capture.init(RESOLUTION, afio, gpioa, rcc);
+    capture.init(RESOLUTION, p.AFIO, p.GPIOA, p.RCC);
 }
 
-// IDLE LOOP
-fn idle(ref prio: P0, ref thr: T0) -> ! {
+fn idle(r: idle::Resources) -> ! {
     const CHANNELS: [Channel; 4] =
         [Channel::_1, Channel::_2, Channel::_3, Channel::_4];
 
-    let itm = ITM.access(prio, thr);
-    let tim1 = TIM1.access(prio, thr);
-
-    let capture = Capture(&*tim1);
+    let capture = Capture(r.TIM1);
 
     for c in &CHANNELS {
         capture.enable(*c);
@@ -79,7 +51,7 @@ fn idle(ref prio: P0, ref thr: T0) -> ! {
         for c in &CHANNELS {
             match capture.capture(*c) {
                 Ok(snapshot) => {
-                    iprintln!(&itm.stim[0], "{:?}: {:?} ms", c, snapshot);
+                    iprintln!(&r.ITM.stim[0], "{:?}: {:?} ms", c, snapshot);
                 }
                 Err(nb::Error::WouldBlock) => {}
                 Err(nb::Error::Other(e)) => panic!("{:?}", e),
@@ -87,6 +59,3 @@ fn idle(ref prio: P0, ref thr: T0) -> ! {
         }
     }
 }
-
-// TASKS
-tasks!(stm32f103xx, {});
diff --git a/examples/capture2.rs b/examples/capture2.rs
index f9884181fa067a755442a83f0579bdc1cbfad46e..8005c9bc30112d13c785811058de25e6152bc493 100644
--- a/examples/capture2.rs
+++ b/examples/capture2.rs
@@ -1,75 +1,47 @@
 //! Input capture using TIM2
 
 #![deny(warnings)]
-#![feature(const_fn)]
-#![feature(used)]
+#![feature(plugin)]
 #![no_std]
+#![plugin(cortex_m_rtfm_macros)]
 
 extern crate blue_pill;
-
-#[macro_use]
+#[macro_use(iprint, iprintln)]
 extern crate cortex_m;
-
-extern crate embedded_hal as hal;
-
-// version = "0.2.3"
-extern crate cortex_m_rt;
-
-// version = "0.1.0"
-#[macro_use]
 extern crate cortex_m_rtfm as rtfm;
-
 extern crate nb;
 
-use blue_pill::stm32f103xx;
 use blue_pill::time::Milliseconds;
 use blue_pill::{Capture, Channel};
-use hal::prelude::*;
-use rtfm::{P0, T0, TMax};
+use blue_pill::prelude::*;
 
 // CONFIGURATION
 const RESOLUTION: Milliseconds = Milliseconds(1);
 
-// RESOURCES
-peripherals!(stm32f103xx, {
-    AFIO: Peripheral {
-        ceiling: C0,
-    },
-    GPIOA: Peripheral {
-        ceiling: C0,
-    },
-    ITM: Peripheral {
-        ceiling: C0,
-    },
-    RCC: Peripheral {
-        ceiling: C0,
-    },
-    TIM2: Peripheral {
-        ceiling: C0,
+rtfm! {
+    device: blue_pill::stm32f103xx,
+
+    init: {
+        path: init,
     },
-});
 
-// INITIALIZATION PHASE
-fn init(ref prio: P0, thr: &TMax) {
-    let afio = &AFIO.access(prio, thr);
-    let gpioa = &GPIOA.access(prio, thr);
-    let rcc = &RCC.access(prio, thr);
-    let tim2 = TIM2.access(prio, thr);
+    idle: {
+        path: idle,
+        resources: [ITM, TIM2],
+    },
+}
 
-    let capture = Capture(&*tim2);
+fn init(p: init::Peripherals) {
+    let capture = Capture(p.TIM2);
 
-    capture.init(RESOLUTION, afio, gpioa, rcc);
+    capture.init(RESOLUTION, p.AFIO, p.GPIOA, p.RCC);
 }
 
-// IDLE LOOP
-fn idle(ref prio: P0, ref thr: T0) -> ! {
+fn idle(r: idle::Resources) -> ! {
     const CHANNELS: [Channel; 4] =
         [Channel::_1, Channel::_2, Channel::_3, Channel::_4];
 
-    let itm = ITM.access(prio, thr);
-    let tim2 = TIM2.access(prio, thr);
-
-    let capture = Capture(&*tim2);
+    let capture = Capture(r.TIM2);
 
     for c in &CHANNELS {
         capture.enable(*c);
@@ -79,7 +51,7 @@ fn idle(ref prio: P0, ref thr: T0) -> ! {
         for c in &CHANNELS {
             match capture.capture(*c) {
                 Ok(snapshot) => {
-                    iprintln!(&itm.stim[0], "{:?}: {:?} ms", c, snapshot);
+                    iprintln!(&r.ITM.stim[0], "{:?}: {:?} ms", c, snapshot);
                 }
                 Err(nb::Error::WouldBlock) => {}
                 Err(nb::Error::Other(e)) => panic!("{:?}", e),
@@ -87,6 +59,3 @@ fn idle(ref prio: P0, ref thr: T0) -> ! {
         }
     }
 }
-
-// TASKS
-tasks!(stm32f103xx, {});
diff --git a/examples/capture3.rs b/examples/capture3.rs
index 84bb71ecef118ce493e9296f3b01c8418e1472c2..5d35e11d16fc5c7dae12a6847c9cb9ddb3b1b207 100644
--- a/examples/capture3.rs
+++ b/examples/capture3.rs
@@ -1,74 +1,46 @@
 //! Input capture using TIM3
 
 #![deny(warnings)]
-#![feature(const_fn)]
-#![feature(used)]
+#![feature(plugin)]
 #![no_std]
+#![plugin(cortex_m_rtfm_macros)]
 
 extern crate blue_pill;
-
-#[macro_use]
+#[macro_use(iprint, iprintln)]
 extern crate cortex_m;
-
-extern crate embedded_hal as hal;
-
-// version = "0.2.3"
-extern crate cortex_m_rt;
-
-// version = "0.1.0"
-#[macro_use]
 extern crate cortex_m_rtfm as rtfm;
-
 extern crate nb;
 
-use blue_pill::stm32f103xx;
+use blue_pill::prelude::*;
 use blue_pill::time::Milliseconds;
 use blue_pill::{Capture, Channel};
-use hal::prelude::*;
-use rtfm::{P0, T0, TMax};
 
 // CONFIGURATION
 const RESOLUTION: Milliseconds = Milliseconds(1);
 
-// RESOURCES
-peripherals!(stm32f103xx, {
-    AFIO: Peripheral {
-        ceiling: C0,
-    },
-    GPIOA: Peripheral {
-        ceiling: C0,
-    },
-    ITM: Peripheral {
-        ceiling: C0,
-    },
-    RCC: Peripheral {
-        ceiling: C0,
-    },
-    TIM3: Peripheral {
-        ceiling: C0,
+rtfm! {
+    device: blue_pill::stm32f103xx,
+
+    init: {
+        path: init,
     },
-});
 
-// INITIALIZATION PHASE
-fn init(ref prio: P0, thr: &TMax) {
-    let afio = &AFIO.access(prio, thr);
-    let gpioa = &GPIOA.access(prio, thr);
-    let rcc = &RCC.access(prio, thr);
-    let tim3 = TIM3.access(prio, thr);
+    idle: {
+        path: idle,
+        resources: [ITM, TIM3],
+    },
+}
 
-    let capture = Capture(&*tim3);
+fn init(p: init::Peripherals) {
+    let capture = Capture(p.TIM3);
 
-    capture.init(RESOLUTION, afio, gpioa, rcc);
+    capture.init(RESOLUTION, p.AFIO, p.GPIOA, p.RCC);
 }
 
-// IDLE LOOP
-fn idle(ref prio: P0, ref thr: T0) -> ! {
+fn idle(r: idle::Resources) -> ! {
     const CHANNELS: [Channel; 2] = [Channel::_1, Channel::_2];
 
-    let itm = ITM.access(prio, thr);
-    let tim3 = TIM3.access(prio, thr);
-
-    let capture = Capture(&*tim3);
+    let capture = Capture(r.TIM3);
 
     for c in &CHANNELS {
         capture.enable(*c);
@@ -78,7 +50,7 @@ fn idle(ref prio: P0, ref thr: T0) -> ! {
         for c in &CHANNELS {
             match capture.capture(*c) {
                 Ok(snapshot) => {
-                    iprintln!(&itm.stim[0], "{:?}: {:?} ms", c, snapshot);
+                    iprintln!(&r.ITM.stim[0], "{:?}: {:?} ms", c, snapshot);
                 }
                 Err(nb::Error::WouldBlock) => {}
                 Err(nb::Error::Other(e)) => panic!("{:?}", e),
@@ -86,6 +58,3 @@ fn idle(ref prio: P0, ref thr: T0) -> ! {
         }
     }
 }
-
-// TASKS
-tasks!(stm32f103xx, {});
diff --git a/examples/capture4.rs b/examples/capture4.rs
index c0539cd796b7df143adb61693972b9a8cda69a25..b08142aaa4ab54712c82d91fc0b3cfa68bca8e36 100644
--- a/examples/capture4.rs
+++ b/examples/capture4.rs
@@ -1,75 +1,47 @@
 //! Input capture using TIM4
 
 #![deny(warnings)]
-#![feature(const_fn)]
-#![feature(used)]
+#![feature(plugin)]
 #![no_std]
+#![plugin(cortex_m_rtfm_macros)]
 
 extern crate blue_pill;
-
 #[macro_use]
 extern crate cortex_m;
-
-extern crate embedded_hal as hal;
-
-// version = "0.2.3"
-extern crate cortex_m_rt;
-
-// version = "0.1.0"
-#[macro_use]
 extern crate cortex_m_rtfm as rtfm;
-
 extern crate nb;
 
-use blue_pill::stm32f103xx;
 use blue_pill::time::Milliseconds;
 use blue_pill::{Capture, Channel};
-use hal::prelude::*;
-use rtfm::{P0, T0, TMax};
+use blue_pill::prelude::*;
 
 // CONFIGURATION
 const RESOLUTION: Milliseconds = Milliseconds(1);
 
-// RESOURCES
-peripherals!(stm32f103xx, {
-    AFIO: Peripheral {
-        ceiling: C0,
-    },
-    GPIOB: Peripheral {
-        ceiling: C0,
-    },
-    ITM: Peripheral {
-        ceiling: C0,
-    },
-    RCC: Peripheral {
-        ceiling: C0,
-    },
-    TIM4: Peripheral {
-        ceiling: C0,
+rtfm! {
+    device: blue_pill::stm32f103xx,
+
+    init: {
+        path: init,
     },
-});
 
-// INITIALIZATION PHASE
-fn init(ref prio: P0, thr: &TMax) {
-    let afio = &AFIO.access(prio, thr);
-    let gpiob = &GPIOB.access(prio, thr);
-    let rcc = &RCC.access(prio, thr);
-    let tim4 = TIM4.access(prio, thr);
+    idle: {
+        path: idle,
+        resources: [ITM, TIM4],
+    },
+}
 
-    let capture = Capture(&*tim4);
+fn init(p: init::Peripherals) {
+    let capture = Capture(p.TIM4);
 
-    capture.init(RESOLUTION, afio, gpiob, rcc);
+    capture.init(RESOLUTION, p.AFIO, p.GPIOB, p.RCC);
 }
 
-// IDLE LOOP
-fn idle(ref prio: P0, ref thr: T0) -> ! {
+fn idle(r: idle::Resources) -> ! {
     const CHANNELS: [Channel; 4] =
         [Channel::_1, Channel::_2, Channel::_3, Channel::_4];
 
-    let itm = ITM.access(prio, thr);
-    let tim4 = TIM4.access(prio, thr);
-
-    let capture = Capture(&*tim4);
+    let capture = Capture(r.TIM4);
 
     for c in &CHANNELS {
         capture.enable(*c);
@@ -79,7 +51,7 @@ fn idle(ref prio: P0, ref thr: T0) -> ! {
         for c in &CHANNELS {
             match capture.capture(*c) {
                 Ok(snapshot) => {
-                    iprintln!(&itm.stim[0], "{:?}: {:?} ms", c, snapshot);
+                    iprintln!(&r.ITM.stim[0], "{:?}: {:?} ms", c, snapshot);
                 }
                 Err(nb::Error::WouldBlock) => {}
                 Err(nb::Error::Other(e)) => panic!("{:?}", e),
@@ -87,6 +59,3 @@ fn idle(ref prio: P0, ref thr: T0) -> ! {
         }
     }
 }
-
-// TASKS
-tasks!(stm32f103xx, {});
diff --git a/examples/concurrent.rs b/examples/concurrent.rs
index a3ae9f35137387d3c74ecd823da55a52bc9e9003..26a1d9fa63182aa96c54cb6d267c097481c9cbb2 100644
--- a/examples/concurrent.rs
+++ b/examples/concurrent.rs
@@ -1,79 +1,67 @@
 //! Serial loopback
 
-#![feature(const_fn)]
-#![feature(used)]
+#![deny(warnings)]
+#![feature(plugin)]
 #![no_std]
+#![plugin(cortex_m_rtfm_macros)]
 
 extern crate blue_pill;
 
-extern crate embedded_hal as hal;
-
-// version = "0.2.3"
-extern crate cortex_m_rt;
-
-// version = "0.1.0"
 #[macro_use]
 extern crate cortex_m_rtfm as rtfm;
 
-extern crate nb;
-
 use blue_pill::led::{self, Green};
+use blue_pill::prelude::*;
 use blue_pill::serial::Event;
 use blue_pill::time::Hertz;
 use blue_pill::{Serial, Timer, stm32f103xx};
-use hal::prelude::*;
-use rtfm::{Local, P0, P1, T0, T1, TMax};
-use stm32f103xx::interrupt::{TIM1_UP_TIM10, USART1};
+use rtfm::Threshold;
 
-// CONFIGURATION
-pub const BAUD_RATE: Hertz = Hertz(115_200);
-pub const FREQUENCY: Hertz = Hertz(1);
+rtfm! {
+    device: stm32f103xx,
 
-// RESOURCES
-peripherals!(stm32f103xx, {
-    AFIO: Peripheral {
-        ceiling: C0,
+    init: {
+        path: init,
     },
-    GPIOA: Peripheral {
-        ceiling: C0,
-    },
-    GPIOC: Peripheral {
-        ceiling: C0,
-    },
-    RCC: Peripheral {
-        ceiling: C0,
-    },
-    USART1: Peripheral {
-        ceiling: C1,
+
+    idle: {
+        path: idle,
     },
-    TIM1: Peripheral {
-        ceiling: C1,
+
+    tasks: {
+        TIM2: {
+            priority: 1,
+            enabled: true,
+            resources: [TIM2],
+        },
+        USART1: {
+            priority: 1,
+            enabled: true,
+            resources: [USART1],
+        },
     },
-});
+}
 
-// INITIALIZATION PHASE
-fn init(ref prio: P0, thr: &TMax) {
-    let afio = &AFIO.access(prio, thr);
-    let gpioa = &GPIOA.access(prio, thr);
-    let gpioc = &GPIOC.access(prio, thr);
-    let rcc = &RCC.access(prio, thr);
-    let usart1 = USART1.access(prio, thr);
-    let tim1 = TIM1.access(prio, thr);
+// CONFIGURATION
+pub const BAUD_RATE: Hertz = Hertz(115_200);
+pub const FREQUENCY: Hertz = Hertz(1);
 
-    let serial = Serial(&*usart1);
-    let timer = Timer(&*tim1);
+// INITIALIZATION PHASE
+fn init(p: init::Peripherals) {
+    let serial = Serial(p.USART1);
+    let timer = Timer(p.TIM2);
 
-    led::init(gpioc, rcc);
+    led::init(p.GPIOC, p.RCC);
 
-    serial.init(BAUD_RATE.invert(), afio, None, gpioa, rcc);
+    serial.init(BAUD_RATE.invert(), p.AFIO, None, p.GPIOA, p.RCC);
     serial.listen(Event::Rxne);
 
-    timer.init(FREQUENCY.invert(), rcc);
+    timer.init(FREQUENCY.invert(), p.RCC);
     timer.resume();
 }
 
 // IDLE LOOP
-fn idle(_prio: P0, _thr: T0) -> ! {
+fn idle() -> ! {
     // Sleep
     loop {
         rtfm::wfi();
@@ -81,47 +69,29 @@ fn idle(_prio: P0, _thr: T0) -> ! {
 }
 
 // TASKS
-tasks!(stm32f103xx, {
-    blinky: Task {
-        interrupt: TIM1_UP_TIM10,
-        priority: P1,
-        enabled: true,
-    },
-    loopback: Task {
-        interrupt: USART1,
-        priority: P1,
-        enabled: true,
-    },
+task!(TIM2, blinky, Local {
+    state: bool = false;
 });
 
-fn blinky(ref mut task: TIM1_UP_TIM10, ref prio: P1, ref thr: T1) {
-    static STATE: Local<bool, TIM1_UP_TIM10> = Local::new(false);
-
-    let state = STATE.borrow_mut(task);
-    let tim1 = TIM1.access(prio, thr);
+fn blinky(_t: Threshold, l: &mut Local, r: TIM2::Resources) {
+    let timer = Timer(r.TIM2);
 
-    let timer = Timer(&*tim1);
+    timer.wait().unwrap();
 
-    // NOTE(unwrap) timeout should have already occurred
-    timer.wait().unwrap_or_else(|_| unreachable!());
+    l.state = !l.state;
 
-    *state = !*state;
-
-    if *state {
+    if l.state {
         Green.on();
     } else {
         Green.off();
     }
 }
 
-fn loopback(_task: USART1, ref prio: P1, ref thr: T1) {
-    let usart1 = USART1.access(prio, thr);
+task!(USART1, loopback);
 
-    let serial = Serial(&*usart1);
+fn loopback(_t: Threshold, r: USART1::Resources) {
+    let serial = Serial(r.USART1);
 
-    match serial.read().and_then(|byte| serial.write(byte)) {
-        Err(nb::Error::Other(e)) => panic!("{:?}", e),
-        Err(nb::Error::WouldBlock) => unreachable!(),
-        Ok(()) => {}
-    }
+    let byte = serial.read().unwrap();
+    serial.write(byte).unwrap();
 }
diff --git a/examples/cpu.rs b/examples/cpu.rs
index e179bd56781ab48e7aec165be5f8ee362ed70c00..a86bde9afc29665d3ef964707cdef659bca7c000 100644
--- a/examples/cpu.rs
+++ b/examples/cpu.rs
@@ -1,115 +1,96 @@
 //! CPU usage monitor
 
+#![deny(warnings)]
 #![feature(const_fn)]
-#![feature(used)]
+#![feature(plugin)]
 #![no_std]
+#![plugin(cortex_m_rtfm_macros)]
 
 extern crate blue_pill;
 
-// version = "0.2.9"
-#[macro_use]
+#[macro_use(iprint, iprintln)]
 extern crate cortex_m;
 
-extern crate embedded_hal as hal;
-
-// version = "0.2.4"
-extern crate cortex_m_rt;
-
-// version = "0.1.0"
 #[macro_use]
 extern crate cortex_m_rtfm as rtfm;
 
-use core::cell::Cell;
-
 use blue_pill::Timer;
 use blue_pill::stm32f103xx;
 use blue_pill::time::Hertz;
-use hal::prelude::*;
-use rtfm::{C1, P0, P1, Resource, T0, T1, TMax};
-use stm32f103xx::interrupt::TIM1_UP_TIM10;
+use blue_pill::prelude::*;
+use rtfm::Threshold;
 
-// CONFIGURATION
-const FREQUENCY: Hertz = Hertz(1);
+rtfm! {
+    device: stm32f103xx,
 
-// RESOURCES
-peripherals!(stm32f103xx, {
-    DWT: Peripheral {
-        ceiling: C0,
+    resources: {
+        SLEEP_TIME: u32 = 0;
     },
-    ITM: Peripheral {
-        ceiling: C1,
+
+    init: {
+        path: init,
     },
-    RCC: Peripheral {
-        ceiling: C0,
+
+    idle: {
+        path: idle,
+        resources: [DWT, SLEEP_TIME],
     },
-    TIM1: Peripheral {
-        ceiling: C1,
+
+    tasks: {
+        TIM2: {
+            priority: 1,
+            enabled: true,
+            resources: [ITM, SLEEP_TIME, TIM2],
+        },
     },
-});
+}
 
-// Total sleep time (in clock cycles)
-static SLEEP_TIME: Resource<Cell<u32>, C1> = Resource::new(Cell::new(0));
+// CONFIGURATION
+const FREQUENCY: Hertz = Hertz(1);
 
 // INITIALIZATION PHASE
-fn init(ref prio: P0, thr: &TMax) {
-    let dwt = &DWT.access(prio, thr);
-    let rcc = &RCC.access(prio, thr);
-    let tim1 = TIM1.access(prio, thr);
+fn init(p: init::Peripherals, _r: init::Resources) {
+    let timer = Timer(p.TIM2);
 
-    let timer = Timer(&*tim1);
+    p.DWT.enable_cycle_counter();
 
-    dwt.enable_cycle_counter();
-
-    timer.init(FREQUENCY.invert(), rcc);
+    timer.init(FREQUENCY.invert(), p.RCC);
     timer.resume();
 }
 
 // IDLE LOOP
-fn idle(ref prio: P0, _thr: T0) -> ! {
+fn idle(_t: Threshold, mut r: idle::Resources) -> ! {
     loop {
         // For the span of this critical section the processor will not service
         // interrupts (tasks)
-        rtfm::atomic(|thr| {
-            let dwt = DWT.access(prio, thr);
-            let sleep_time = SLEEP_TIME.access(prio, thr);
+        rtfm::atomic(|cs| {
+            let sleep_time = r.SLEEP_TIME.borrow_mut(cs);
 
             // Sleep
-            let before = dwt.cyccnt.read();
+            let before = r.DWT.cyccnt.read();
             rtfm::wfi();
-            let after = dwt.cyccnt.read();
+            let after = r.DWT.cyccnt.read();
 
             let elapsed = after.wrapping_sub(before);
 
             // Accumulate sleep time
-            sleep_time.set(sleep_time.get() + elapsed);
+            **sleep_time += elapsed;
         });
 
         // Tasks are serviced at this point
     }
 }
 
-// TASKS
-tasks!(stm32f103xx, {
-    periodic: Task {
-        interrupt: TIM1_UP_TIM10,
-        priority: P1,
-        enabled: true,
-    },
-});
-
-fn periodic(_task: TIM1_UP_TIM10, ref prio: P1, ref thr: T1) {
-    let itm = ITM.access(prio, thr);
-    let sleep_time = SLEEP_TIME.access(prio, thr);
-    let tim1 = TIM1.access(prio, thr);
+task!(TIM2, periodic);
 
-    let timer = Timer(&*tim1);
+fn periodic(_t: Threshold, r: TIM2::Resources) {
+    let timer = Timer(r.TIM2);
 
-    // NOTE(unwrap) timeout should have already occurred
-    timer.wait().unwrap_or_else(|_| unreachable!());
+    timer.wait().unwrap();
 
     // Report clock cycles spent sleeping
-    iprintln!(&itm.stim[0], "{}", sleep_time.get());
+    iprintln!(&r.ITM.stim[0], "{}", **r.SLEEP_TIME);
 
     // Reset sleep time back to zero
-    sleep_time.set(0);
+    **r.SLEEP_TIME = 0;
 }
diff --git a/examples/gpio.rs b/examples/gpio.rs
index 7afa9d1cd553a964575c05fddbca5306480f1be2..a246d9435ba19c71c41b3e238d89e562163bb652 100644
--- a/examples/gpio.rs
+++ b/examples/gpio.rs
@@ -1,42 +1,32 @@
 //! Set PB12 high
 
-#![feature(const_fn)]
-#![feature(used)]
+#![deny(warnings)]
+#![feature(plugin)]
 #![no_std]
+#![plugin(cortex_m_rtfm_macros)]
 
 extern crate blue_pill;
-
-// version = "0.2.3"
-extern crate cortex_m_rt;
-
-// version = "0.1.0"
-#[macro_use]
 extern crate cortex_m_rtfm as rtfm;
 
 use blue_pill::gpio::{self, PB12};
-use blue_pill::stm32f103xx;
-use rtfm::{P0, T0, TMax};
 
-// RESOURCES
-peripherals!(stm32f103xx, {
-    GPIOB: Peripheral {
-        ceiling: C0,
-    },
-    RCC: Peripheral {
-        ceiling: C0,
+rtfm! {
+    device: blue_pill::stm32f103xx,
+
+    init: {
+        path: init,
     },
-});
 
-// INITIALIZATION PHASE
-fn init(ref prio: P0, thr: &TMax) {
-    let gpiob = &GPIOB.access(prio, thr);
-    let rcc = &RCC.access(prio, thr);
+    idle: {
+        path: idle,
+    },
+}
 
-    gpio::init(gpiob, rcc);
+fn init(p: init::Peripherals) {
+    gpio::init(p.GPIOB, p.RCC);
 }
 
-// IDLE LOOP
-fn idle(_prio: P0, _thr: T0) -> ! {
+fn idle() -> ! {
     PB12.high();
 
     // Sleep
@@ -44,6 +34,3 @@ fn idle(_prio: P0, _thr: T0) -> ! {
         rtfm::wfi();
     }
 }
-
-// TASKS
-tasks!(stm32f103xx, {});
diff --git a/examples/hello.rs b/examples/hello.rs
index cf62b61d954122f0a9ff609cf0c591b55f3ea835..3bf593348f4a732fea40b669f9cbf348bd312223 100644
--- a/examples/hello.rs
+++ b/examples/hello.rs
@@ -1,38 +1,54 @@
 //! Prints "Hello" and then "World" on the OpenOCD console
 
-#![feature(used)]
+#![deny(warnings)]
+#![feature(const_fn)]
+#![feature(plugin)]
 #![no_std]
+#![plugin(cortex_m_rtfm_macros)]
 
 extern crate blue_pill;
-
-// version = "0.2.9"
-#[macro_use]
 extern crate cortex_m;
+extern crate cortex_m_rtfm as rtfm;
+extern crate cortex_m_semihosting;
 
-// version = "0.2.3"
-extern crate cortex_m_rt;
+use core::fmt::Write;
 
-// version = "0.1.0"
-#[macro_use]
-extern crate cortex_m_rtfm as rtfm;
+use cortex_m_semihosting::hio::{self, HStdout};
 
-use blue_pill::stm32f103xx;
-use rtfm::{P0, T0, TMax};
+rtfm! {
+    device: blue_pill::stm32f103xx,
+
+    resources: {
+        HSTDOUT: Option<HStdout> = None;
+    },
+
+    init: {
+        path: init,
+    },
+
+    idle: {
+        path: idle,
+        resources: [HSTDOUT],
+    },
+}
 
 // INITIALIZATION PHASE
-fn init(_prio: P0, _thr: &TMax) {
-    hprintln!("Hello");
+fn init(_p: init::Peripherals, r: init::Resources) {
+    let mut hstdout = hio::hstdout().unwrap();
+
+    writeln!(hstdout, "Hello").unwrap();
+
+    **r.HSTDOUT = Some(hstdout);
 }
 
 // IDLE LOOP
-fn idle(_prio: P0, _thr: T0) -> ! {
-    hprintln!("World");
+fn idle(r: idle::Resources) -> ! {
+    if let Some(mut hstdout) = r.HSTDOUT.take() {
+        writeln!(hstdout, "World").unwrap();
+    }
 
     // Sleep
     loop {
         rtfm::wfi();
     }
 }
-
-// TASKS
-tasks!(stm32f103xx, {});
diff --git a/examples/itm.rs b/examples/itm.rs
index 8d79c1c49a3eb986818fdc7e0d796bbdd92b8bfb..106193c3f8b0989511cf89c3dc8e0211b4987c35 100644
--- a/examples/itm.rs
+++ b/examples/itm.rs
@@ -19,51 +19,37 @@
 //! World
 //! ```
 
-#![feature(const_fn)]
-#![feature(used)]
+#![feature(plugin)]
 #![no_std]
+#![plugin(cortex_m_rtfm_macros)]
 
 extern crate blue_pill;
-
-// version = "0.2.9"
-#[macro_use]
+#[macro_use(iprint, iprintln)]
 extern crate cortex_m;
-
-// version = "0.2.3"
-extern crate cortex_m_rt;
-
-// version = "0.1.0"
-#[macro_use]
 extern crate cortex_m_rtfm as rtfm;
 
-use blue_pill::stm32f103xx;
-use rtfm::{P0, T0, TMax};
+rtfm! {
+    device: blue_pill::stm32f103xx,
 
-// RESOURCES
-peripherals!(stm32f103xx, {
-    ITM: Peripheral {
-        ceiling: C0,
+    init: {
+        path: init,
     },
-});
-
-// INITIALIZATION PHASE
-fn init(ref prio: P0, thr: &TMax) {
-    let itm = ITM.access(prio, thr);
 
-    iprintln!(&itm.stim[0], "Hello");
+    idle: {
+        path: idle,
+        resources: [ITM],
+    },
 }
 
-// IDLE LOOP
-fn idle(ref prio: P0, ref thr: T0) -> ! {
-    let itm = ITM.access(prio, thr);
+fn init(p: init::Peripherals) {
+    iprintln!(&p.ITM.stim[0], "Hello");
+}
 
-    iprintln!(&itm.stim[0], "World");
+fn idle(r: idle::Resources) -> ! {
+    iprintln!(&r.ITM.stim[0], "World");
 
     // Sleep
     loop {
         rtfm::wfi();
     }
 }
-
-// TASKS
-tasks!(stm32f103xx, {});
diff --git a/examples/led.rs b/examples/led.rs
index 62a10e87a68092a3e4da9276b73237e4c1da3d62..b890356568c0732469037f141029d83df12775dd 100644
--- a/examples/led.rs
+++ b/examples/led.rs
@@ -1,42 +1,32 @@
 //! Turns the user LED on
 
-#![feature(const_fn)]
-#![feature(used)]
+#![deny(warnings)]
+#![feature(plugin)]
 #![no_std]
+#![plugin(cortex_m_rtfm_macros)]
 
 extern crate blue_pill;
-
-// version = "0.2.3"
-extern crate cortex_m_rt;
-
-// version = "0.1.0"
-#[macro_use]
 extern crate cortex_m_rtfm as rtfm;
 
 use blue_pill::led::{self, Green};
-use blue_pill::stm32f103xx;
-use rtfm::{P0, T0, TMax};
 
-// RESOURCES
-peripherals!(stm32f103xx, {
-    GPIOC: Peripheral {
-        ceiling: C0,
-    },
-    RCC: Peripheral {
-        ceiling: C0,
+rtfm! {
+    device: blue_pill::stm32f103xx,
+
+    init: {
+        path: init,
     },
-});
 
-// INITIALIZATION PHASE
-fn init(ref prio: P0, thr: &TMax) {
-    let gpioc = &GPIOC.access(prio, thr);
-    let rcc = &RCC.access(prio, thr);
+    idle: {
+        path: idle,
+    },
+}
 
-    led::init(gpioc, rcc);
+fn init(p: init::Peripherals) {
+    led::init(p.GPIOC, p.RCC);
 }
 
-// IDLE LOOP
-fn idle(_prio: P0, _thr: T0) -> ! {
+fn idle() -> ! {
     Green.on();
 
     // Sleep
@@ -44,6 +34,3 @@ fn idle(_prio: P0, _thr: T0) -> ! {
         rtfm::wfi();
     }
 }
-
-// TASKS
-tasks!(stm32f103xx, {});
diff --git a/examples/loopback.rs b/examples/loopback.rs
index e3397d37d601a2acaa2b652b39744e2b78fb4bad..00e675b8b89e731bf1e629d5ba82e6a6c6822413 100644
--- a/examples/loopback.rs
+++ b/examples/loopback.rs
@@ -1,80 +1,60 @@
 //! Serial loopback via USART1
 
-#![feature(const_fn)]
-#![feature(used)]
+#![deny(warnings)]
+#![feature(plugin)]
 #![no_std]
+#![plugin(cortex_m_rtfm_macros)]
 
 extern crate blue_pill;
-
-extern crate embedded_hal as hal;
-
-// version = "0.2.3"
-extern crate cortex_m_rt;
-
-// version = "0.1.0"
-#[macro_use]
+#[macro_use(task)]
 extern crate cortex_m_rtfm as rtfm;
 
+use blue_pill::Serial;
+use blue_pill::prelude::*;
 use blue_pill::serial::Event;
 use blue_pill::time::Hertz;
-use blue_pill::{Serial, stm32f103xx};
-use hal::prelude::*;
-use rtfm::{P0, P1, T0, T1, TMax};
-use stm32f103xx::interrupt::USART1;
+use rtfm::Threshold;
 
 // CONFIGURATION
 pub const BAUD_RATE: Hertz = Hertz(115_200);
 
-// RESOURCES
-peripherals!(stm32f103xx, {
-    AFIO: Peripheral {
-        ceiling: C0,
-    },
-    GPIOA: Peripheral {
-        ceiling: C0,
-    },
-    RCC: Peripheral {
-        ceiling: C0,
+rtfm! {
+    device: blue_pill::stm32f103xx,
+
+    init: {
+        path: init,
     },
-    USART1: Peripheral {
-        ceiling: C1,
+
+    idle: {
+        path: idle,
     },
-});
 
-// INITIALIZATION PHASE
-fn init(ref prio: P0, thr: &TMax) {
-    let afio = &AFIO.access(prio, thr);
-    let gpioa = &GPIOA.access(prio, thr);
-    let rcc = &RCC.access(prio, thr);
-    let usart1 = USART1.access(prio, thr);
+    tasks: {
+        USART1: {
+            enabled: true,
+            priority: 1,
+            resources: [USART1],
+        },
+    },
+}
 
-    let serial = Serial(&*usart1);
+fn init(p: init::Peripherals) {
+    let serial = Serial(p.USART1);
 
-    serial.init(BAUD_RATE.invert(), afio, None, gpioa, rcc);
+    serial.init(BAUD_RATE.invert(), p.AFIO, None, p.GPIOA, p.RCC);
     serial.listen(Event::Rxne);
 }
 
-// IDLE LOOP
-fn idle(_prio: P0, _thr: T0) -> ! {
-    // Sleep
+fn idle() -> ! {
     loop {
         rtfm::wfi();
     }
 }
 
-// TASKS
-tasks!(stm32f103xx, {
-    loopback: Task {
-        interrupt: USART1,
-        priority: P1,
-        enabled: true,
-    },
-});
-
-fn loopback(_task: USART1, ref prio: P1, ref thr: T1) {
-    let usart1 = USART1.access(prio, thr);
+task!(USART1, loopback);
 
-    let serial = Serial(&*usart1);
+fn loopback(_t: Threshold, r: USART1::Resources) {
+    let serial = Serial(r.USART1);
 
     let byte = serial.read().unwrap();
     serial.write(byte).unwrap();
diff --git a/examples/pwm-control.rs b/examples/pwm-control.rs
index 6c3228d673c48247f9eff1702c491aaa0d190587..142aab606cde9881dfb96f270b9a0ca176253d11 100644
--- a/examples/pwm-control.rs
+++ b/examples/pwm-control.rs
@@ -6,94 +6,68 @@
 //! - '/' decrease duty by a factor of 2
 
 #![deny(warnings)]
-#![feature(const_fn)]
-#![feature(used)]
+#![feature(plugin)]
 #![no_std]
+#![plugin(cortex_m_rtfm_macros)]
 
 extern crate blue_pill;
-
-extern crate embedded_hal as hal;
-
-// version = "0.2.3"
-extern crate cortex_m_rt;
-
-// version = "0.1.0"
-#[macro_use]
+#[macro_use(task)]
 extern crate cortex_m_rtfm as rtfm;
 
 use core::u16;
 
+use blue_pill::prelude::*;
 use blue_pill::time::Hertz;
-use blue_pill::{Channel, Pwm, Serial, stm32f103xx};
-use hal::prelude::*;
-use rtfm::{P0, P1, T0, T1, TMax};
-use stm32f103xx::interrupt::USART1;
+use blue_pill::{Channel, Pwm, Serial};
+use rtfm::Threshold;
 
 // CONFIGURATION
 const BAUD_RATE: Hertz = Hertz(115_200);
 const FREQUENCY: Hertz = Hertz(1_000);
 
-// RESOURCES
-peripherals!(stm32f103xx, {
-    AFIO: Peripheral {
-        ceiling: C0,
-    },
-    GPIOA: Peripheral {
-        ceiling: C0,
-    },
-    RCC: Peripheral {
-        ceiling: C0,
-    },
-    TIM2: Peripheral {
-        ceiling: C1,
+rtfm! {
+    device: blue_pill::stm32f103xx,
+
+    init: {
+        path: init,
     },
-    USART1: Peripheral {
-        ceiling: C1,
+
+    idle: {
+        path: idle,
     },
-});
 
-// INITIALIZATION PHASE
-fn init(ref prio: P0, thr: &TMax) {
-    let afio = &AFIO.access(prio, thr);
-    let gpioa = &GPIOA.access(prio, thr);
-    let rcc = &RCC.access(prio, thr);
-    let tim2 = TIM2.access(prio, thr);
-    let usart1 = USART1.access(prio, thr);
+    tasks: {
+        USART1: {
+            enabled: true,
+            priority: 1,
+            resources: [TIM2, USART1],
+        },
+    },
+}
 
-    let pwm = Pwm(&*tim2);
-    let serial = Serial(&*usart1);
+fn init(p: init::Peripherals) {
+    let pwm = Pwm(p.TIM2);
+    let serial = Serial(p.USART1);
 
-    serial.init(BAUD_RATE.invert(), afio, None, gpioa, rcc);
+    serial.init(BAUD_RATE.invert(), p.AFIO, None, p.GPIOA, p.RCC);
 
-    pwm.init(FREQUENCY.invert(), afio, None, gpioa, rcc);
+    pwm.init(FREQUENCY.invert(), p.AFIO, None, p.GPIOA, p.RCC);
     pwm.set_duty(Channel::_1, 0);
 
     pwm.enable(Channel::_1);
 }
 
-// IDLE LOOP
-fn idle(_prio: P0, _thr: T0) -> ! {
-    // Sleep
+fn idle() -> ! {
     loop {
         rtfm::wfi();
     }
 }
 
-// TASKS
-tasks!(stm32f103xx, {
-    rx: Task {
-        interrupt: USART1,
-        priority: P1,
-        enabled: true,
-    },
-});
-
-fn rx(_task: USART1, ref prio: P1, ref thr: T1) {
-    let tim2 = TIM2.access(prio, thr);
-    let usart1 = USART1.access(prio, thr);
+task!(USART1, rx);
 
-    let pwm = Pwm(&*tim2);
-    let serial = Serial(&*usart1);
+fn rx(_t: Threshold, r: USART1::Resources) {
+    let pwm = Pwm(r.TIM2);
+    let serial = Serial(r.USART1);
 
     let byte = serial.read().unwrap();
     // Echo back to signal we are alive
diff --git a/examples/pwm1.rs b/examples/pwm1.rs
index 4608af33886b182ab4e0761bdf993da8f90dc745..0bda209447e8f4c662271b6267cae460b71b4500 100644
--- a/examples/pwm1.rs
+++ b/examples/pwm1.rs
@@ -2,55 +2,36 @@
 // FIXME doesn't seem to work :-(
 
 #![deny(warnings)]
-#![feature(const_fn)]
-#![feature(used)]
+#![feature(plugin)]
 #![no_std]
+#![plugin(cortex_m_rtfm_macros)]
 
 extern crate blue_pill;
-
-extern crate embedded_hal as hal;
-
-// version = "0.2.3"
-extern crate cortex_m_rt;
-
-// version = "0.1.0"
-#[macro_use]
 extern crate cortex_m_rtfm as rtfm;
 
-use blue_pill::{Channel, Pwm, stm32f103xx};
+use blue_pill::prelude::*;
 use blue_pill::time::Hertz;
-use hal::prelude::*;
-use rtfm::{P0, T0, TMax};
+use blue_pill::{Channel, Pwm};
 
 // CONFIGURATION
 const FREQUENCY: Hertz = Hertz(1_000);
 
-// RESOURCES
-peripherals!(stm32f103xx, {
-    AFIO: Peripheral {
-        ceiling: C0,
-    },
-    GPIOA: Peripheral {
-        ceiling: C0,
-    },
-    RCC: Peripheral {
-        ceiling: C0,
-    },
-    TIM1: Peripheral {
-        ceiling: C0,
+rtfm! {
+    device: blue_pill::stm32f103xx,
+
+    init: {
+        path: init,
     },
-});
 
-// INITIALIZATION PHASE
-fn init(ref prio: P0, thr: &TMax) {
-    let afio = &AFIO.access(prio, thr);
-    let gpioa = &GPIOA.access(prio, thr);
-    let rcc = &RCC.access(prio, thr);
-    let tim1 = TIM1.access(prio, thr);
+    idle: {
+        path: idle,
+    },
+}
 
-    let pwm = Pwm(&*tim1);
+fn init(p: init::Peripherals) {
+    let pwm = Pwm(p.TIM1);
 
-    pwm.init(FREQUENCY.invert(), afio, gpioa, rcc);
+    pwm.init(FREQUENCY.invert(), p.AFIO, p.GPIOA, p.RCC);
     let duty = pwm.get_max_duty() / 16;
 
     const CHANNELS: [Channel; 4] =
@@ -66,13 +47,8 @@ fn init(ref prio: P0, thr: &TMax) {
     }
 }
 
-// IDLE LOOP
-fn idle(_prio: P0, _thr: T0) -> ! {
-    // Sleep
+fn idle() -> ! {
     loop {
         rtfm::wfi();
     }
 }
-
-// TASKS
-tasks!(stm32f103xx, {});
diff --git a/examples/pwm2.rs b/examples/pwm2.rs
index 5d1388dc52e39bbf2c376ee997e44a0b05ecc9e0..5d9afed219041527da0dbdc1e8dc37fdb93aff33 100644
--- a/examples/pwm2.rs
+++ b/examples/pwm2.rs
@@ -1,55 +1,36 @@
 //! Output a PWM with a duty cycle of ~6% on all the channels of TIM2
 
 #![deny(warnings)]
-#![feature(const_fn)]
-#![feature(used)]
+#![feature(plugin)]
 #![no_std]
+#![plugin(cortex_m_rtfm_macros)]
 
 extern crate blue_pill;
-
-extern crate embedded_hal as hal;
-
-// version = "0.2.3"
-extern crate cortex_m_rt;
-
-// version = "0.1.0"
-#[macro_use]
 extern crate cortex_m_rtfm as rtfm;
 
-use blue_pill::{Channel, Pwm, stm32f103xx};
+use blue_pill::prelude::*;
 use blue_pill::time::Hertz;
-use hal::prelude::*;
-use rtfm::{P0, T0, TMax};
+use blue_pill::{Channel, Pwm};
 
 // CONFIGURATION
 const FREQUENCY: Hertz = Hertz(1_000); // Hz
 
-// RESOURCES
-peripherals!(stm32f103xx, {
-    AFIO: Peripheral {
-        ceiling: C0,
-    },
-    GPIOA: Peripheral {
-        ceiling: C0,
-    },
-    RCC: Peripheral {
-        ceiling: C0,
-    },
-    TIM2: Peripheral {
-        ceiling: C0,
+rtfm! {
+    device: blue_pill::stm32f103xx,
+
+    init: {
+        path: init,
     },
-});
 
-// INITIALIZATION PHASE
-fn init(ref prio: P0, thr: &TMax) {
-    let afio = &AFIO.access(prio, thr);
-    let gpioa = &GPIOA.access(prio, thr);
-    let rcc = &RCC.access(prio, thr);
-    let tim2 = TIM2.access(prio, thr);
+    idle: {
+        path: idle,
+    },
+}
 
-    let pwm = Pwm(&*tim2);
+fn init(p: init::Peripherals) {
+    let pwm = Pwm(p.TIM2);
 
-    pwm.init(FREQUENCY.invert(), afio, None, gpioa, rcc);
+    pwm.init(FREQUENCY.invert(), p.AFIO, None, p.GPIOA, p.RCC);
     let duty = pwm.get_max_duty() / 16;
 
     const CHANNELS: [Channel; 4] =
@@ -65,13 +46,8 @@ fn init(ref prio: P0, thr: &TMax) {
     }
 }
 
-// IDLE LOOP
-fn idle(_prio: P0, _thr: T0) -> ! {
-    // Sleep
+fn idle() -> ! {
     loop {
         rtfm::wfi();
     }
 }
-
-// TASKS
-tasks!(stm32f103xx, {});
diff --git a/examples/pwm3.rs b/examples/pwm3.rs
index d2e112625e69401e9c620e9383560090b76995bb..4d0413e960a2ce24f98add8da2ca855d6d862bd1 100644
--- a/examples/pwm3.rs
+++ b/examples/pwm3.rs
@@ -1,55 +1,36 @@
 //! Output a PWM with a duty cycle of ~6% on all the channels of TIM3
 
 #![deny(warnings)]
-#![feature(const_fn)]
-#![feature(used)]
+#![feature(plugin)]
 #![no_std]
+#![plugin(cortex_m_rtfm_macros)]
 
 extern crate blue_pill;
-
-extern crate embedded_hal as hal;
-
-// version = "0.2.3"
-extern crate cortex_m_rt;
-
-// version = "0.1.0"
-#[macro_use]
 extern crate cortex_m_rtfm as rtfm;
 
-use blue_pill::{Channel, Pwm, stm32f103xx};
+use blue_pill::{Channel, Pwm};
 use blue_pill::time::Hertz;
-use hal::prelude::*;
-use rtfm::{P0, T0, TMax};
+use blue_pill::prelude::*;
 
 // CONFIGURATION
 const FREQUENCY: Hertz = Hertz(1_000);
 
-// RESOURCES
-peripherals!(stm32f103xx, {
-    AFIO: Peripheral {
-        ceiling: C0,
-    },
-    GPIOA: Peripheral {
-        ceiling: C0,
-    },
-    RCC: Peripheral {
-        ceiling: C0,
-    },
-    TIM3: Peripheral {
-        ceiling: C0,
+rtfm! {
+    device: blue_pill::stm32f103xx,
+
+    init: {
+        path: init,
     },
-});
 
-// INITIALIZATION PHASE
-fn init(ref prio: P0, thr: &TMax) {
-    let afio = &AFIO.access(prio, thr);
-    let gpioa = &GPIOA.access(prio, thr);
-    let rcc = &RCC.access(prio, thr);
-    let tim3 = TIM3.access(prio, thr);
+    idle: {
+        path: idle,
+    },
+}
 
-    let pwm = Pwm(&*tim3);
+fn init(p: init::Peripherals) {
+    let pwm = Pwm(p.TIM3);
 
-    pwm.init(FREQUENCY.invert(), afio, None, gpioa, rcc);
+    pwm.init(FREQUENCY.invert(), p.AFIO, None, p.GPIOA, p.RCC);
     let duty = pwm.get_max_duty() / 16;
 
     const CHANNELS: [Channel; 2] = [Channel::_1, Channel::_2];
@@ -64,13 +45,8 @@ fn init(ref prio: P0, thr: &TMax) {
     }
 }
 
-// IDLE LOOP
-fn idle(_prio: P0, _thr: T0) -> ! {
-    // Sleep
+fn idle() -> ! {
     loop {
         rtfm::wfi();
     }
 }
-
-// TASKS
-tasks!(stm32f103xx, {});
diff --git a/examples/pwm4.rs b/examples/pwm4.rs
index 4a83b861d588a4a0dec3986eb81a1237e738ae3d..bdf4aa6e1002ba8d000971b2a1670048a8590b9f 100644
--- a/examples/pwm4.rs
+++ b/examples/pwm4.rs
@@ -1,55 +1,36 @@
 //! Output a PWM with a duty cycle of ~6% on all the channels of TIM4
 
 #![deny(warnings)]
-#![feature(const_fn)]
-#![feature(used)]
+#![feature(plugin)]
 #![no_std]
+#![plugin(cortex_m_rtfm_macros)]
 
 extern crate blue_pill;
-
-extern crate embedded_hal as hal;
-
-// version = "0.2.3"
-extern crate cortex_m_rt;
-
-// version = "0.1.0"
-#[macro_use]
 extern crate cortex_m_rtfm as rtfm;
 
-use blue_pill::{Channel, Pwm, stm32f103xx};
+use blue_pill::prelude::*;
 use blue_pill::time::Hertz;
-use hal::prelude::*;
-use rtfm::{P0, T0, TMax};
+use blue_pill::{Channel, Pwm};
 
 // CONFIGURATION
 const FREQUENCY: Hertz = Hertz(1_000);
 
-// RESOURCES
-peripherals!(stm32f103xx, {
-    AFIO: Peripheral {
-        ceiling: C0,
-    },
-    GPIOB: Peripheral {
-        ceiling: C0,
-    },
-    RCC: Peripheral {
-        ceiling: C0,
-    },
-    TIM4: Peripheral {
-        ceiling: C0,
+rtfm! {
+    device: blue_pill::stm32f103xx,
+
+    init: {
+        path: init,
     },
-});
 
-// INITIALIZATION PHASE
-fn init(ref prio: P0, thr: &TMax) {
-    let afio = &AFIO.access(prio, thr);
-    let gpiob = &GPIOB.access(prio, thr);
-    let rcc = &RCC.access(prio, thr);
-    let tim4 = TIM4.access(prio, thr);
+    idle: {
+        path: idle,
+    },
+}
 
-    let pwm = Pwm(&*tim4);
+fn init(p: init::Peripherals) {
+    let pwm = Pwm(p.TIM4);
 
-    pwm.init(FREQUENCY.invert(), afio, None, gpiob, rcc);
+    pwm.init(FREQUENCY.invert(), p.AFIO, None, p.GPIOB, p.RCC);
     let duty = pwm.get_max_duty() / 16;
 
     const CHANNELS: [Channel; 4] =
@@ -65,13 +46,8 @@ fn init(ref prio: P0, thr: &TMax) {
     }
 }
 
-// IDLE LOOP
-fn idle(_prio: P0, _thr: T0) -> ! {
-    // Sleep
+fn idle() -> ! {
     loop {
         rtfm::wfi();
     }
 }
-
-// TASKS
-tasks!(stm32f103xx, {});
diff --git a/examples/qei1.rs b/examples/qei1.rs
index e5b1306fe068802a17239149e30697eaf55a6121..97320b65891f39911d4a00ceca65eb28b046d463 100644
--- a/examples/qei1.rs
+++ b/examples/qei1.rs
@@ -3,99 +3,67 @@
 //! Periodically reports the readings of the QEI
 
 #![deny(warnings)]
-#![feature(const_fn)]
-#![feature(used)]
+#![feature(plugin)]
 #![no_std]
+#![plugin(cortex_m_rtfm_macros)]
 
 extern crate blue_pill;
-
-extern crate embedded_hal as hal;
-
-#[macro_use]
+#[macro_use(iprint, iprintln)]
 extern crate cortex_m;
-
-// version = "0.2.3"
-extern crate cortex_m_rt;
-
-// version = "0.1.0"
-#[macro_use]
+#[macro_use(task)]
 extern crate cortex_m_rtfm as rtfm;
 
+use blue_pill::prelude::*;
 use blue_pill::time::Hertz;
-use blue_pill::{Qei, Timer, stm32f103xx};
-use hal::prelude::*;
-use rtfm::{Local, P0, P1, T0, T1, TMax};
-use stm32f103xx::interrupt::TIM4;
+use blue_pill::{Qei, Timer};
+use rtfm::Threshold;
 
 // CONFIGURATION
 const FREQUENCY: Hertz = Hertz(1);
 
-// RESOURCES
-peripherals!(stm32f103xx, {
-    AFIO: Peripheral {
-        ceiling: C0,
-    },
-    GPIOA: Peripheral {
-        ceiling: C0,
-    },
-    ITM: Peripheral {
-        ceiling: C1,
-    },
-    RCC: Peripheral {
-        ceiling: C0,
-    },
-    TIM1: Peripheral {
-        ceiling: C1,
+rtfm! {
+    device: blue_pill::stm32f103xx,
+
+    init: {
+        path: init,
     },
-    TIM4: Peripheral {
-        ceiling: C1,
+
+    idle: {
+        path: idle,
     },
-});
 
-// INITIALIZATION PHASE
-fn init(ref prio: P0, thr: &TMax) {
-    let afio = &AFIO.access(prio, thr);
-    let gpioa = &GPIOA.access(prio, thr);
-    let rcc = &RCC.access(prio, thr);
-    let tim1 = TIM1.access(prio, thr);
-    let tim4 = TIM4.access(prio, thr);
+    tasks: {
+        TIM4: {
+            enabled: true,
+            priority: 1,
+            resources: [ITM, TIM1, TIM4],
+        },
+    },
+}
 
-    let qei = Qei(&*tim1);
-    let timer = Timer(&*tim4);
+fn init(p: init::Peripherals) {
+    let qei = Qei(p.TIM1);
+    let timer = Timer(p.TIM4);
 
-    qei.init(afio, gpioa, rcc);
+    qei.init(p.AFIO, p.GPIOA, p.RCC);
 
-    timer.init(FREQUENCY.invert(), rcc);
+    timer.init(FREQUENCY.invert(), p.RCC);
     timer.resume();
 }
 
-// IDLE LOOP
-fn idle(_prio: P0, _thr: T0) -> ! {
-    // Sleep
+fn idle() -> ! {
     loop {
         rtfm::wfi();
     }
 }
 
-// TASKS
-tasks!(stm32f103xx, {
-    periodic: Task {
-        interrupt: TIM4,
-        priority: P1,
-        enabled: true,
-    },
+task!(TIM4, periodic, Locals {
+    previous: Option<u16> = None;
 });
 
-fn periodic(ref mut task: TIM4, ref prio: P1, ref thr: T1) {
-    static PREVIOUS: Local<Option<u16>, TIM4> = Local::new(None);
-
-    let itm = &ITM.access(prio, thr);
-    let previous = PREVIOUS.borrow_mut(task);
-    let tim1 = TIM1.access(prio, thr);
-    let tim4 = TIM4.access(prio, thr);
-
-    let qei = Qei(&*tim1);
-    let timer = Timer(&*tim4);
+fn periodic(_t: Threshold, l: &mut Locals, r: TIM4::Resources) {
+    let qei = Qei(r.TIM1);
+    let timer = Timer(r.TIM4);
 
     // NOTE(unwrap) timeout should have already occurred
     timer.wait().unwrap_or_else(|_| unreachable!());
@@ -103,11 +71,11 @@ fn periodic(ref mut task: TIM4, ref prio: P1, ref thr: T1) {
     let curr = qei.count();
     let dir = qei.direction();
 
-    if let Some(prev) = previous.take() {
+    if let Some(prev) = l.previous.take() {
         let speed = (curr as i16).wrapping_sub(prev as i16);
 
-        iprintln!(&itm.stim[0], "{} - {} - {:?}", curr, speed, dir);
+        iprintln!(&r.ITM.stim[0], "{} - {} - {:?}", curr, speed, dir);
     }
 
-    *previous = Some(curr);
+    l.previous = Some(curr);
 }
diff --git a/examples/qei2.rs b/examples/qei2.rs
index efbe8dfe578581c7fda133c204d6dd6111c3c652..f1f63a3841e63c6d853a5d952029ca34806c236d 100644
--- a/examples/qei2.rs
+++ b/examples/qei2.rs
@@ -3,111 +3,79 @@
 //! Periodically reports the readings of the QEI
 
 #![deny(warnings)]
-#![feature(const_fn)]
-#![feature(used)]
+#![feature(plugin)]
 #![no_std]
+#![plugin(cortex_m_rtfm_macros)]
 
 extern crate blue_pill;
-
-extern crate embedded_hal as hal;
-
-#[macro_use]
+#[macro_use(iprint, iprintln)]
 extern crate cortex_m;
-
-// version = "0.2.3"
-extern crate cortex_m_rt;
-
-// version = "0.1.0"
-#[macro_use]
+#[macro_use(task)]
 extern crate cortex_m_rtfm as rtfm;
 
+use blue_pill::prelude::*;
 use blue_pill::time::Hertz;
-use blue_pill::{Qei, Timer, stm32f103xx};
-use hal::prelude::*;
-use rtfm::{Local, P0, P1, T0, T1, TMax};
-use stm32f103xx::interrupt::TIM4;
+use blue_pill::{Qei, Timer};
+use rtfm::Threshold;
 
 // CONFIGURATION
 const FREQUENCY: Hertz = Hertz(1);
 
-// RESOURCES
-peripherals!(stm32f103xx, {
-    AFIO: Peripheral {
-        ceiling: C0,
-    },
-    GPIOA: Peripheral {
-        ceiling: C0,
-    },
-    ITM: Peripheral {
-        ceiling: C1,
-    },
-    RCC: Peripheral {
-        ceiling: C0,
-    },
-    TIM2: Peripheral {
-        ceiling: C1,
+rtfm! {
+    device: blue_pill::stm32f103xx,
+
+    init: {
+        path: init,
     },
-    TIM4: Peripheral {
-        ceiling: C1,
+
+    idle: {
+        path: idle,
     },
-});
 
-// INITIALIZATION PHASE
-fn init(ref prio: P0, thr: &TMax) {
-    let afio = &AFIO.access(prio, thr);
-    let gpioa = &GPIOA.access(prio, thr);
-    let rcc = &RCC.access(prio, thr);
-    let tim2 = TIM2.access(prio, thr);
-    let tim4 = TIM4.access(prio, thr);
+    tasks: {
+        TIM4: {
+            enabled: true,
+            priority: 1,
+            resources: [ITM, TIM2, TIM4],
+        },
+    },
+}
 
-    let qei = Qei(&*tim2);
-    let timer = Timer(&*tim4);
+fn init(p: init::Peripherals) {
+    let qei = Qei(p.TIM2);
+    let timer = Timer(p.TIM4);
 
-    qei.init(afio, gpioa, rcc);
+    qei.init(p.AFIO, p.GPIOA, p.RCC);
 
-    timer.init(FREQUENCY.invert(), rcc);
+    timer.init(FREQUENCY.invert(), p.RCC);
     timer.resume();
 }
 
-// IDLE LOOP
-fn idle(_prio: P0, _thr: T0) -> ! {
-    // Sleep
+fn idle() -> ! {
     loop {
         rtfm::wfi();
     }
 }
 
-// TASKS
-tasks!(stm32f103xx, {
-    periodic: Task {
-        interrupt: TIM4,
-        priority: P1,
-        enabled: true,
-    },
+task!(TIM4, periodic, Locals {
+    previous: Option<u16> = None;
 });
 
-fn periodic(ref mut task: TIM4, ref prio: P1, ref thr: T1) {
-    static PREVIOUS: Local<Option<u16>, TIM4> = Local::new(None);
-
-    let itm = &ITM.access(prio, thr);
-    let previous = PREVIOUS.borrow_mut(task);
-    let tim2 = TIM2.access(prio, thr);
-    let tim4 = TIM4.access(prio, thr);
-
-    let qei = Qei(&*tim2);
-    let timer = Timer(&*tim4);
+fn periodic(_t: Threshold, l: &mut Locals, r: TIM4::Resources) {
+    let qei = Qei(r.TIM2);
+    let timer = Timer(r.TIM4);
 
     // NOTE(unwrap) timeout should have already occurred
-    timer.wait().unwrap_or_else(|_| unreachable!());
+    timer.wait().unwrap();
 
     let curr = qei.count();
     let dir = qei.direction();
 
-    if let Some(prev) = previous.take() {
+    if let Some(prev) = l.previous.take() {
         let speed = (curr as i16).wrapping_sub(prev as i16);
 
-        iprintln!(&itm.stim[0], "{} - {} - {:?}", curr, speed, dir);
+        iprintln!(&r.ITM.stim[0], "{} - {} - {:?}", curr, speed, dir);
     }
 
-    *previous = Some(curr);
+    l.previous = Some(curr);
 }
diff --git a/examples/qei3.rs b/examples/qei3.rs
index dcc03575da46d48d79263a4d14d9bc0ebda2ba58..d1afc67417ee0a9ac8d95fa64ddf7ecbdfcef451 100644
--- a/examples/qei3.rs
+++ b/examples/qei3.rs
@@ -3,111 +3,78 @@
 //! Periodically reports the readings of the QEI
 
 #![deny(warnings)]
-#![feature(const_fn)]
-#![feature(used)]
+#![feature(plugin)]
 #![no_std]
+#![plugin(cortex_m_rtfm_macros)]
 
 extern crate blue_pill;
-
-extern crate embedded_hal as hal;
-
-#[macro_use]
+#[macro_use(iprint, iprintln)]
 extern crate cortex_m;
-
-// version = "0.2.3"
-extern crate cortex_m_rt;
-
-// version = "0.1.0"
-#[macro_use]
+#[macro_use(task)]
 extern crate cortex_m_rtfm as rtfm;
 
 use blue_pill::time::Hertz;
-use blue_pill::{Qei, Timer, stm32f103xx};
-use hal::prelude::*;
-use rtfm::{Local, P0, P1, T0, T1, TMax};
-use stm32f103xx::interrupt::TIM4;
+use blue_pill::{Qei, Timer};
+use blue_pill::prelude::*;
+use rtfm::Threshold;
 
 // CONFIGURATION
 const FREQUENCY: Hertz = Hertz(1);
 
-// RESOURCES
-peripherals!(stm32f103xx, {
-    AFIO: Peripheral {
-        ceiling: C0,
-    },
-    GPIOA: Peripheral {
-        ceiling: C0,
-    },
-    ITM: Peripheral {
-        ceiling: C1,
-    },
-    RCC: Peripheral {
-        ceiling: C0,
-    },
-    TIM3: Peripheral {
-        ceiling: C1,
+rtfm! {
+    device: blue_pill::stm32f103xx,
+
+    init: {
+        path: init,
     },
-    TIM4: Peripheral {
-        ceiling: C1,
+
+    idle: {
+        path: idle,
     },
-});
 
-// INITIALIZATION PHASE
-fn init(ref prio: P0, thr: &TMax) {
-    let afio = &AFIO.access(prio, thr);
-    let gpioa = &GPIOA.access(prio, thr);
-    let rcc = &RCC.access(prio, thr);
-    let tim3 = TIM3.access(prio, thr);
-    let tim4 = TIM4.access(prio, thr);
+    tasks: {
+        TIM4: {
+            enabled: true,
+            priority: 1,
+            resources: [ITM, TIM3, TIM4],
+        },
+    },
+}
 
-    let qei = Qei(&*tim3);
-    let timer = Timer(&*tim4);
+fn init(p: init::Peripherals) {
+    let qei = Qei(p.TIM3);
+    let timer = Timer(p.TIM4);
 
-    qei.init(afio, gpioa, rcc);
+    qei.init(p.AFIO, p.GPIOA, p.RCC);
 
-    timer.init(FREQUENCY.invert(), rcc);
+    timer.init(FREQUENCY.invert(), p.RCC);
     timer.resume();
 }
 
-// IDLE LOOP
-fn idle(_prio: P0, _thr: T0) -> ! {
-    // Sleep
+fn idle() -> ! {
     loop {
         rtfm::wfi();
     }
 }
 
-// TASKS
-tasks!(stm32f103xx, {
-    periodic: Task {
-        interrupt: TIM4,
-        priority: P1,
-        enabled: true,
-    },
+task!(TIM4, periodic, Locals {
+    previous: Option<u16> = None;
 });
 
-fn periodic(ref mut task: TIM4, ref prio: P1, ref thr: T1) {
-    static PREVIOUS: Local<Option<u16>, TIM4> = Local::new(None);
-
-    let itm = &ITM.access(prio, thr);
-    let previous = PREVIOUS.borrow_mut(task);
-    let tim3 = TIM3.access(prio, thr);
-    let tim4 = TIM4.access(prio, thr);
-
-    let qei = Qei(&*tim3);
-    let timer = Timer(&*tim4);
+fn periodic(_t: Threshold, l: &mut Locals, r: TIM4::Resources) {
+    let qei = Qei(r.TIM3);
+    let timer = Timer(r.TIM4);
 
-    // NOTE(unwrap) timeout should have already occurred
-    timer.wait().unwrap_or_else(|_| unreachable!());
+    timer.wait().unwrap();
 
     let curr = qei.count();
     let dir = qei.direction();
 
-    if let Some(prev) = previous.take() {
+    if let Some(prev) = l.previous.take() {
         let speed = (curr as i16).wrapping_sub(prev as i16);
 
-        iprintln!(&itm.stim[0], "{} - {} - {:?}", curr, speed, dir);
+        iprintln!(&r.ITM.stim[0], "{} - {} - {:?}", curr, speed, dir);
     }
 
-    *previous = Some(curr);
+    l.previous = Some(curr);
 }
diff --git a/examples/qei4.rs b/examples/qei4.rs
index 323368420852949ac917948b86d071f72ade473b..728e067690a4be0dbbbe2fe09c4425edeeea7411 100644
--- a/examples/qei4.rs
+++ b/examples/qei4.rs
@@ -3,111 +3,78 @@
 //! Periodically reports the readings of the QEI
 
 #![deny(warnings)]
-#![feature(const_fn)]
-#![feature(used)]
+#![feature(plugin)]
 #![no_std]
+#![plugin(cortex_m_rtfm_macros)]
 
 extern crate blue_pill;
-
-extern crate embedded_hal as hal;
-
-#[macro_use]
+#[macro_use(iprint, iprintln)]
 extern crate cortex_m;
-
-// version = "0.2.3"
-extern crate cortex_m_rt;
-
-// version = "0.1.0"
-#[macro_use]
+#[macro_use(task)]
 extern crate cortex_m_rtfm as rtfm;
 
 use blue_pill::time::Hertz;
-use blue_pill::{Qei, Timer, stm32f103xx};
-use hal::prelude::*;
-use rtfm::{Local, P0, P1, T0, T1, TMax};
-use stm32f103xx::interrupt::TIM1_UP_TIM10;
+use blue_pill::{Qei, Timer};
+use blue_pill::prelude::*;
+use rtfm::Threshold;
 
 // CONFIGURATION
 const FREQUENCY: Hertz = Hertz(1);
 
-// RESOURCES
-peripherals!(stm32f103xx, {
-    AFIO: Peripheral {
-        ceiling: C0,
-    },
-    GPIOB: Peripheral {
-        ceiling: C0,
-    },
-    ITM: Peripheral {
-        ceiling: C1,
-    },
-    RCC: Peripheral {
-        ceiling: C0,
-    },
-    TIM1: Peripheral {
-        ceiling: C1,
+rtfm! {
+    device: blue_pill::stm32f103xx,
+
+    init: {
+        path: init,
     },
-    TIM4: Peripheral {
-        ceiling: C1,
+
+    idle: {
+        path: idle,
     },
-});
 
-// INITIALIZATION PHASE
-fn init(ref prio: P0, thr: &TMax) {
-    let afio = &AFIO.access(prio, thr);
-    let gpiob = &GPIOB.access(prio, thr);
-    let rcc = &RCC.access(prio, thr);
-    let tim1 = TIM1.access(prio, thr);
-    let tim4 = TIM4.access(prio, thr);
+    tasks: {
+        TIM1_UP_TIM10: {
+            enabled: true,
+            priority: 1,
+            resources: [ITM, TIM1, TIM4],
+        },
+    },
+}
 
-    let qei = Qei(&*tim4);
-    let timer = Timer(&*tim1);
+fn init(p: init::Peripherals) {
+    let qei = Qei(p.TIM4);
+    let timer = Timer(p.TIM1);
 
-    qei.init(afio, gpiob, rcc);
+    qei.init(p.AFIO, p.GPIOB, p.RCC);
 
-    timer.init(FREQUENCY.invert(), rcc);
+    timer.init(FREQUENCY.invert(), p.RCC);
     timer.resume();
 }
 
-// IDLE LOOP
-fn idle(_prio: P0, _thr: T0) -> ! {
-    // Sleep
+fn idle() -> ! {
     loop {
         rtfm::wfi();
     }
 }
 
-// TASKS
-tasks!(stm32f103xx, {
-    periodic: Task {
-        interrupt: TIM1_UP_TIM10,
-        priority: P1,
-        enabled: true,
-    },
+task!(TIM1_UP_TIM10, periodic, Locals {
+    previous: Option<u16> = None;
 });
 
-fn periodic(ref mut task: TIM1_UP_TIM10, ref prio: P1, ref thr: T1) {
-    static PREVIOUS: Local<Option<u16>, TIM1_UP_TIM10> = Local::new(None);
-
-    let itm = &ITM.access(prio, thr);
-    let previous = PREVIOUS.borrow_mut(task);
-    let tim1 = TIM1.access(prio, thr);
-    let tim4 = TIM4.access(prio, thr);
-
-    let qei = Qei(&*tim4);
-    let timer = Timer(&*tim1);
+fn periodic(_t: Threshold, l: &mut Locals, r: TIM1_UP_TIM10::Resources) {
+    let qei = Qei(r.TIM4);
+    let timer = Timer(r.TIM1);
 
-    // NOTE(unwrap) timeout should have already occurred
-    timer.wait().unwrap_or_else(|_| unreachable!());
+    timer.wait().unwrap();
 
     let curr = qei.count();
     let dir = qei.direction();
 
-    if let Some(prev) = previous.take() {
+    if let Some(prev) = l.previous.take() {
         let speed = (curr as i16).wrapping_sub(prev as i16);
 
-        iprintln!(&itm.stim[0], "{} - {} - {:?}", curr, speed, dir);
+        iprintln!(&r.ITM.stim[0], "{} - {} - {:?}", curr, speed, dir);
     }
 
-    *previous = Some(curr);
+    l.previous = Some(curr);
 }
diff --git a/examples/spi1.rs b/examples/spi1.rs
index b6b6fd4f0157c4beb7484f5ac84c7d2be135f185..2ef9b0d62abf6396cb6f318997efa1942ea67e43 100644
--- a/examples/spi1.rs
+++ b/examples/spi1.rs
@@ -1,61 +1,38 @@
 //! Interfacing the MPU9250 using SPI1
 
 #![deny(warnings)]
-#![feature(const_fn)]
-#![feature(used)]
+#![feature(plugin)]
 #![no_std]
+#![plugin(cortex_m_rtfm_macros)]
 
 extern crate blue_pill;
-
-#[macro_use]
+#[macro_use(iprint, iprintln)]
 extern crate cortex_m;
-
-extern crate embedded_hal as hal;
-
-// version = "0.2.3"
-extern crate cortex_m_rt;
-
-// version = "0.1.0"
-#[macro_use]
 extern crate cortex_m_rtfm as rtfm;
 
-use blue_pill::{Spi, stm32f103xx};
-use hal::prelude::*;
-use rtfm::{P0, T0, TMax};
+use blue_pill::Spi;
+use blue_pill::prelude::*;
 
-// RESOURCES
-peripherals!(stm32f103xx, {
-    AFIO: Peripheral {
-        ceiling: C0,
-    },
-    GPIOA: Peripheral {
-        ceiling: C0,
-    },
-    ITM: Peripheral {
-        ceiling: C0,
-    },
-    RCC: Peripheral {
-        ceiling: C0,
-    },
-    SPI1: Peripheral {
-        ceiling: C0,
+rtfm! {
+    device: blue_pill::stm32f103xx,
+
+    init: {
+        path: init,
     },
-});
 
-// INITIALIZATION PHASE
-fn init(ref prio: P0, thr: &TMax) {
-    let afio = &AFIO.access(prio, thr);
-    let gpioa = &GPIOA.access(prio, thr);
-    let rcc = &RCC.access(prio, thr);
-    let spi1 = SPI1.access(prio, thr);
+    idle: {
+        path: idle,
+        resources: [ITM, SPI1],
+    },
+}
 
-    let spi = Spi(&*spi1);
+fn init(p: init::Peripherals) {
+    let spi = Spi(p.SPI1);
 
-    spi.init(afio, gpioa, rcc);
+    spi.init(p.AFIO, p.GPIOA, p.RCC);
 }
 
-// IDLE LOOP
-fn idle(ref prio: P0, ref thr: T0) -> ! {
+fn idle(r: idle::Resources) -> ! {
     // Register to read
     const WHO_AM_I: u8 = 117;
 
@@ -68,10 +45,7 @@ fn idle(ref prio: P0, ref thr: T0) -> ! {
     // Read mode
     pub const R: u8 = 1 << 7;
 
-    let itm = &ITM.access(prio, thr);
-    let spi1 = SPI1.access(prio, thr);
-
-    let spi = Spi(&*spi1);
+    let spi = Spi(r.SPI1);
 
     rtfm::bkpt();
 
@@ -96,17 +70,13 @@ fn idle(ref prio: P0, ref thr: T0) -> ! {
 
     spi.disable();
 
-    iprintln!(&itm.stim[0], "TESTING ...");
+    iprintln!(&r.ITM.stim[0], "TESTING ...");
 
     assert_eq!(ans, ANS);
 
-    iprintln!(&itm.stim[0], "OK");
+    iprintln!(&r.ITM.stim[0], "OK");
 
-    // Sleep
     loop {
         rtfm::wfi();
     }
 }
-
-// TASKS
-tasks!(stm32f103xx, {});
diff --git a/examples/spi2.rs b/examples/spi2.rs
index def1c736902a5acf2ba318562915848aeb8c7bbb..59e5fa8cc169bb0a56806dc5b1e53f811188a574 100644
--- a/examples/spi2.rs
+++ b/examples/spi2.rs
@@ -1,61 +1,38 @@
 //! Interfacing the MPU9250 using SPI2
 
 #![deny(warnings)]
-#![feature(const_fn)]
-#![feature(used)]
+#![feature(plugin)]
 #![no_std]
+#![plugin(cortex_m_rtfm_macros)]
 
 extern crate blue_pill;
-
-#[macro_use]
+#[macro_use(iprint, iprintln)]
 extern crate cortex_m;
-
-extern crate embedded_hal as hal;
-
-// version = "0.2.3"
-extern crate cortex_m_rt;
-
-// version = "0.1.0"
-#[macro_use]
 extern crate cortex_m_rtfm as rtfm;
 
-use blue_pill::{Spi, stm32f103xx};
-use hal::prelude::*;
-use rtfm::{P0, T0, TMax};
+use blue_pill::Spi;
+use blue_pill::prelude::*;
 
-// RESOURCES
-peripherals!(stm32f103xx, {
-    AFIO: Peripheral {
-        ceiling: C0,
-    },
-    GPIOB: Peripheral {
-        ceiling: C0,
-    },
-    ITM: Peripheral {
-        ceiling: C0,
-    },
-    RCC: Peripheral {
-        ceiling: C0,
-    },
-    SPI2: Peripheral {
-        ceiling: C0,
+rtfm! {
+    device: blue_pill::stm32f103xx,
+
+    init: {
+        path: init,
     },
-});
 
-// INITIALIZATION PHASE
-fn init(ref prio: P0, thr: &TMax) {
-    let afio = &AFIO.access(prio, thr);
-    let gpiob = &GPIOB.access(prio, thr);
-    let rcc = &RCC.access(prio, thr);
-    let spi2 = SPI2.access(prio, thr);
+    idle: {
+        path: idle,
+        resources: [ITM, SPI2],
+    },
+}
 
-    let spi = Spi(&*spi2);
+fn init(p: init::Peripherals) {
+    let spi = Spi(p.SPI2);
 
-    spi.init(afio, gpiob, rcc);
+    spi.init(p.AFIO, p.GPIOB, p.RCC);
 }
 
-// IDLE LOOP
-fn idle(ref prio: P0, ref thr: T0) -> ! {
+fn idle(r: idle::Resources) -> ! {
     // Register to read
     const WHO_AM_I: u8 = 117;
 
@@ -68,10 +45,7 @@ fn idle(ref prio: P0, ref thr: T0) -> ! {
     // Read mode
     pub const R: u8 = 1 << 7;
 
-    let itm = &ITM.access(prio, thr);
-    let spi2 = SPI2.access(prio, thr);
-
-    let spi = Spi(&*spi2);
+    let spi = Spi(r.SPI2);
 
     rtfm::bkpt();
 
@@ -96,17 +70,14 @@ fn idle(ref prio: P0, ref thr: T0) -> ! {
 
     spi.disable();
 
-    iprintln!(&itm.stim[0], "TESTING ...");
+    iprintln!(&r.ITM.stim[0], "TESTING ...");
 
     assert_eq!(ans, ANS);
 
-    iprintln!(&itm.stim[0], "OK");
+    iprintln!(&r.ITM.stim[0], "OK");
 
     // Sleep
     loop {
         rtfm::wfi();
     }
 }
-
-// TASKS
-tasks!(stm32f103xx, {});
diff --git a/examples/usart1-rx-dma.rs b/examples/usart1-rx-dma.rs
index d83318cd66a503e5901a8462c2ce7eafa0bf7b66..cbecbb3d96180bd1350091b6b8198283879ea12e 100644
--- a/examples/usart1-rx-dma.rs
+++ b/examples/usart1-rx-dma.rs
@@ -1,91 +1,66 @@
 //! Test receiving serial data using the DMA
 
+#![deny(warnings)]
 #![feature(const_fn)]
-#![feature(used)]
+#![feature(plugin)]
 #![no_std]
+#![plugin(cortex_m_rtfm_macros)]
 
 extern crate blue_pill;
-
-extern crate embedded_hal as hal;
-
-// version = "0.2.3"
-extern crate cortex_m_rt;
-
-// version = "0.1.0"
-#[macro_use]
+#[macro_use(task)]
 extern crate cortex_m_rtfm as rtfm;
-
 extern crate nb;
 
+use blue_pill::Serial;
 use blue_pill::dma::{Buffer, Dma1Channel5};
 use blue_pill::time::Hertz;
-use blue_pill::{Serial, stm32f103xx};
-use rtfm::{C1, P0, P1, Resource, T0, T1, TMax};
-use stm32f103xx::interrupt::DMA1_CHANNEL5;
+use rtfm::Threshold;
 
 // CONFIGURATION
 pub const BAUD_RATE: Hertz = Hertz(115_200);
 
-// RESOURCES
-peripherals!(stm32f103xx, {
-    AFIO: Peripheral {
-        ceiling: C0,
-    },
-    DMA1: Peripheral {
-        ceiling: C1,
-    },
-    GPIOA: Peripheral {
-        ceiling: C0,
-    },
-    RCC: Peripheral {
-        ceiling: C0,
+rtfm! {
+    device: blue_pill::stm32f103xx,
+
+    resources: {
+        BUFFER: Buffer<[u8; 8], Dma1Channel5> = Buffer::new([0; 8]);
     },
-    USART1: Peripheral {
-        ceiling: C1,
+
+    init: {
+        path: init,
     },
-});
 
-static BUFFER: Resource<Buffer<[u8; 8], Dma1Channel5>, C1> =
-    Resource::new(Buffer::new([0; 8]));
+    idle: {
+        path: idle,
+    },
 
-// INITIALIZATION PHASE
-fn init(ref prio: P0, thr: &TMax) {
-    let afio = &AFIO.access(prio, thr);
-    let dma1 = &DMA1.access(prio, thr);
-    let gpioa = &GPIOA.access(prio, thr);
-    let rcc = &RCC.access(prio, thr);
-    let usart1 = USART1.access(prio, thr);
-    let buffer = BUFFER.access(prio, thr);
+    tasks: {
+        DMA1_CHANNEL5: {
+            enabled: true,
+            priority: 1,
+            resources: [BUFFER, DMA1],
+        },
+    },
+}
 
-    let serial = Serial(&*usart1);
+fn init(p: init::Peripherals, r: init::Resources) {
+    let serial = Serial(p.USART1);
 
-    serial.init(BAUD_RATE.invert(), afio, Some(dma1), gpioa, rcc);
+    serial.init(BAUD_RATE.invert(), p.AFIO, Some(p.DMA1), p.GPIOA, p.RCC);
 
-    serial.read_exact(dma1, buffer).unwrap();
+    serial.read_exact(p.DMA1, r.BUFFER).unwrap();
 }
 
-// IDLE LOOP
-fn idle(_prio: P0, _thr: T0) -> ! {
-    // Sleep
+fn idle() -> ! {
     loop {
         rtfm::wfi();
     }
 }
 
-// TASKS
-tasks!(stm32f103xx, {
-    done: Task {
-        interrupt: DMA1_CHANNEL5,
-        priority: P1,
-        enabled: true,
-    },
-});
-
-fn done(_task: DMA1_CHANNEL5, ref prio: P1, ref thr: T1) {
-    let buffer = BUFFER.access(prio, thr);
-    let dma1 = &DMA1.access(prio, thr);
+task!(DMA1_CHANNEL5, transfer_done);
 
-    buffer.release(dma1).unwrap();
+fn transfer_done(_t: Threshold, r: DMA1_CHANNEL5::Resources) {
+    r.BUFFER.release(r.DMA1).unwrap();
 
     rtfm::bkpt();
 }
diff --git a/examples/usart1-tx-dma.rs b/examples/usart1-tx-dma.rs
index 42696a465dc712a1cb509f589f1fa12be416edc4..0b8ec18abca1d5543d259a5fefac4e7b40363ead 100644
--- a/examples/usart1-tx-dma.rs
+++ b/examples/usart1-tx-dma.rs
@@ -1,92 +1,67 @@
 //! Test sending serial data using the DMA
 
+#![deny(warnings)]
 #![feature(const_fn)]
-#![feature(used)]
+#![feature(plugin)]
 #![no_std]
+#![plugin(cortex_m_rtfm_macros)]
 
 extern crate blue_pill;
-
-extern crate embedded_hal as hal;
-
-// version = "0.2.3"
-extern crate cortex_m_rt;
-
-// version = "0.1.0"
-#[macro_use]
+#[macro_use(task)]
 extern crate cortex_m_rtfm as rtfm;
-
 extern crate nb;
 
+use blue_pill::Serial;
 use blue_pill::dma::{Buffer, Dma1Channel4};
 use blue_pill::time::Hertz;
-use blue_pill::{Serial, stm32f103xx};
-use rtfm::{C1, P0, P1, Resource, T0, T1, TMax};
-use stm32f103xx::interrupt::DMA1_CHANNEL4;
+use rtfm::Threshold;
 
 // CONFIGURATION
 pub const BAUD_RATE: Hertz = Hertz(115_200);
 
-// RESOURCES
-peripherals!(stm32f103xx, {
-    AFIO: Peripheral {
-        ceiling: C0,
-    },
-    DMA1: Peripheral {
-        ceiling: C1,
-    },
-    GPIOA: Peripheral {
-        ceiling: C0,
-    },
-    RCC: Peripheral {
-        ceiling: C0,
+rtfm! {
+    device: blue_pill::stm32f103xx,
+
+    resources: {
+        BUFFER: Buffer<[u8; 14], Dma1Channel4> = Buffer::new([0; 14]);
     },
-    USART1: Peripheral {
-        ceiling: C1,
+
+    init: {
+        path: init,
     },
-});
 
-static BUFFER: Resource<Buffer<[u8; 14], Dma1Channel4>, C1> =
-    Resource::new(Buffer::new([0; 14]));
+    idle: {
+        path: idle,
+    },
 
-// INITIALIZATION PHASE
-fn init(ref prio: P0, thr: &TMax) {
-    let afio = &AFIO.access(prio, thr);
-    let dma1 = &DMA1.access(prio, thr);
-    let gpioa = &GPIOA.access(prio, thr);
-    let rcc = &RCC.access(prio, thr);
-    let usart1 = USART1.access(prio, thr);
-    let buffer = BUFFER.access(prio, thr);
+    tasks: {
+        DMA1_CHANNEL4: {
+            enabled: true,
+            priority: 1,
+            resources: [BUFFER, DMA1],
+        },
+    },
+}
 
-    let serial = Serial(&*usart1);
+fn init(p: init::Peripherals, r: init::Resources) {
+    let serial = Serial(p.USART1);
 
-    serial.init(BAUD_RATE.invert(), afio, Some(dma1), gpioa, rcc);
-    buffer.borrow_mut().clone_from_slice(b"Hello, world!\n");
+    serial.init(BAUD_RATE.invert(), p.AFIO, Some(p.DMA1), p.GPIOA, p.RCC);
+    r.BUFFER.borrow_mut().clone_from_slice(b"Hello, world!\n");
 
-    serial.write_all(dma1, buffer).unwrap();
+    serial.write_all(p.DMA1, r.BUFFER).unwrap();
 }
 
-// IDLE LOOP
-fn idle(_prio: P0, _thr: T0) -> ! {
-    // Sleep
+fn idle() -> ! {
     loop {
         rtfm::wfi();
     }
 }
 
-// TASKS
-tasks!(stm32f103xx, {
-    done: Task {
-        interrupt: DMA1_CHANNEL4,
-        priority: P1,
-        enabled: true,
-    },
-});
-
-fn done(_task: DMA1_CHANNEL4, ref prio: P1, ref thr: T1) {
-    let buffer = BUFFER.access(prio, thr);
-    let dma1 = &DMA1.access(prio, thr);
+task!(DMA1_CHANNEL4, transfer_done);
 
-    buffer.release(dma1).unwrap();
+fn transfer_done(_t: Threshold, r: DMA1_CHANNEL4::Resources) {
+    r.BUFFER.release(r.DMA1).unwrap();
 
     rtfm::bkpt();
 }
diff --git a/examples/usart1.rs b/examples/usart1.rs
index d97c665adde45dca068f61161d305f0dd22b9791..5dba7dd9b3c41367fd7edbf8a75965e755d1a5d4 100644
--- a/examples/usart1.rs
+++ b/examples/usart1.rs
@@ -2,57 +2,38 @@
 //!
 //! Connect the TX and RX pins to run this test
 
-#![feature(const_fn)]
-#![feature(used)]
+#![deny(warnings)]
+#![feature(plugin)]
 #![no_std]
+#![plugin(cortex_m_rtfm_macros)]
 
 extern crate blue_pill;
-
-extern crate embedded_hal as hal;
-
-// version = "0.2.3"
-extern crate cortex_m_rt;
-
-// version = "0.1.0"
-#[macro_use]
 extern crate cortex_m_rtfm as rtfm;
-
 extern crate nb;
 
+use blue_pill::Serial;
+use blue_pill::prelude::*;
 use blue_pill::time::Hertz;
-use blue_pill::{Serial, stm32f103xx};
-use hal::prelude::*;
-use rtfm::{P0, T0, TMax};
 
 // CONFIGURATION
 pub const BAUD_RATE: Hertz = Hertz(115_200);
 
-// RESOURCES
-peripherals!(stm32f103xx, {
-    AFIO: Peripheral {
-        ceiling: C0,
-    },
-    GPIOA: Peripheral {
-        ceiling: C0,
-    },
-    RCC: Peripheral {
-        ceiling: C0,
-    },
-    USART1: Peripheral {
-        ceiling: C1,
+rtfm! {
+    device: blue_pill::stm32f103xx,
+
+    init: {
+        path: init,
     },
-});
 
-// INITIALIZATION PHASE
-fn init(ref prio: P0, thr: &TMax) {
-    let afio = &AFIO.access(prio, thr);
-    let gpioa = &GPIOA.access(prio, thr);
-    let rcc = &RCC.access(prio, thr);
-    let usart1 = USART1.access(prio, thr);
+    idle: {
+        path: idle,
+    },
+}
 
-    let serial = Serial(&*usart1);
+fn init(p: init::Peripherals) {
+    let serial = Serial(p.USART1);
 
-    serial.init(BAUD_RATE.invert(), afio, None, gpioa, rcc);
+    serial.init(BAUD_RATE.invert(), p.AFIO, None, p.GPIOA, p.RCC);
 
     const BYTE: u8 = b'A';
 
@@ -72,8 +53,7 @@ fn init(ref prio: P0, thr: &TMax) {
     panic!("Timeout")
 }
 
-// IDLE LOOP
-fn idle(_prio: P0, _thr: T0) -> ! {
+fn idle() -> ! {
     // OK
     rtfm::bkpt();
 
@@ -82,6 +62,3 @@ fn idle(_prio: P0, _thr: T0) -> ! {
         rtfm::wfi();
     }
 }
-
-// TASKS
-tasks!(stm32f103xx, {});
diff --git a/examples/usart2.rs b/examples/usart2.rs
index 57ada09943858eeb867c39337fbab6c340f49dff..a8482a8209ede29167a07a0b702ba75a9bee3327 100644
--- a/examples/usart2.rs
+++ b/examples/usart2.rs
@@ -2,58 +2,39 @@
 //!
 //! Connect the TX and RX pins to run this test
 
-#![feature(const_fn)]
-#![feature(used)]
+#![deny(warnings)]
+#![feature(plugin)]
+#![plugin(cortex_m_rtfm_macros)]
 #![no_std]
 
 extern crate blue_pill;
-
-extern crate embedded_hal as hal;
-
-// version = "0.2.3"
-extern crate cortex_m_rt;
-
-// version = "0.1.0"
-#[macro_use]
 extern crate cortex_m_rtfm as rtfm;
-
 extern crate nb;
 
-use blue_pill::{Serial, stm32f103xx};
+use blue_pill::Serial;
 use blue_pill::time::Hertz;
-use hal::prelude::*;
+use blue_pill::prelude::*;
 use nb::Error;
-use rtfm::{P0, T0, TMax};
 
 // CONFIGURATION
 pub const BAUD_RATE: Hertz = Hertz(115_200);
 
-// RESOURCES
-peripherals!(stm32f103xx, {
-    AFIO: Peripheral {
-        ceiling: C0,
-    },
-    GPIOA: Peripheral {
-        ceiling: C0,
-    },
-    RCC: Peripheral {
-        ceiling: C0,
-    },
-    USART2: Peripheral {
-        ceiling: C1,
+rtfm! {
+    device: blue_pill::stm32f103xx,
+
+    init: {
+        path: init,
     },
-});
 
-// INITIALIZATION PHASE
-fn init(ref prio: P0, thr: &TMax) {
-    let afio = &AFIO.access(prio, thr);
-    let gpioa = &GPIOA.access(prio, thr);
-    let rcc = &RCC.access(prio, thr);
-    let usart2 = USART2.access(prio, thr);
+    idle: {
+        path: idle,
+    },
+}
 
-    let serial = Serial(&*usart2);
+fn init(p: init::Peripherals) {
+    let serial = Serial(p.USART2);
 
-    serial.init(BAUD_RATE.invert(), afio, None, gpioa, rcc);
+    serial.init(BAUD_RATE.invert(), p.AFIO, None, p.GPIOA, p.RCC);
 
     const BYTE: u8 = b'A';
 
@@ -73,8 +54,7 @@ fn init(ref prio: P0, thr: &TMax) {
     panic!("Timeout")
 }
 
-// IDLE LOOP
-fn idle(_prio: P0, _thr: T0) -> ! {
+fn idle() -> ! {
     // OK
     rtfm::bkpt();
 
@@ -83,6 +63,3 @@ fn idle(_prio: P0, _thr: T0) -> ! {
         rtfm::wfi();
     }
 }
-
-// TASKS
-tasks!(stm32f103xx, {});
diff --git a/examples/usart3.rs b/examples/usart3.rs
index f618d0e1d71d59149118abd469a33d5975823ea6..afb3e7bebae11768e57b4fd3f886590967339ef5 100644
--- a/examples/usart3.rs
+++ b/examples/usart3.rs
@@ -2,58 +2,39 @@
 //!
 //! Connect the TX and RX pins to run this test
 
-#![feature(const_fn)]
-#![feature(used)]
+#![deny(warnings)]
+#![feature(plugin)]
 #![no_std]
+#![plugin(cortex_m_rtfm_macros)]
 
 extern crate blue_pill;
-
-extern crate embedded_hal as hal;
-
-// version = "0.2.3"
-extern crate cortex_m_rt;
-
-// version = "0.1.0"
-#[macro_use]
 extern crate cortex_m_rtfm as rtfm;
-
 extern crate nb;
 
-use blue_pill::{Serial, stm32f103xx};
+use blue_pill::Serial;
 use blue_pill::time::Hertz;
-use hal::prelude::*;
+use blue_pill::prelude::*;
 use nb::Error;
-use rtfm::{P0, T0, TMax};
 
 // CONFIGURATION
 pub const BAUD_RATE: Hertz = Hertz(115_200);
 
-// RESOURCES
-peripherals!(stm32f103xx, {
-    AFIO: Peripheral {
-        ceiling: C0,
-    },
-    GPIOB: Peripheral {
-        ceiling: C0,
-    },
-    RCC: Peripheral {
-        ceiling: C0,
-    },
-    USART3: Peripheral {
-        ceiling: C1,
+rtfm! {
+    device: blue_pill::stm32f103xx,
+
+    init: {
+        path: init,
     },
-});
 
-// INITIALIZATION PHASE
-fn init(ref prio: P0, thr: &TMax) {
-    let afio = &AFIO.access(prio, thr);
-    let gpiob = &GPIOB.access(prio, thr);
-    let rcc = &RCC.access(prio, thr);
-    let usart3 = USART3.access(prio, thr);
+    idle: {
+        path: idle,
+    },
+}
 
-    let serial = Serial(&*usart3);
+fn init(p: init::Peripherals) {
+    let serial = Serial(p.USART3);
 
-    serial.init(BAUD_RATE.invert(), afio, None, gpiob, rcc);
+    serial.init(BAUD_RATE.invert(), p.AFIO, None, p.GPIOB, p.RCC);
 
     const BYTE: u8 = b'A';
 
@@ -73,8 +54,7 @@ fn init(ref prio: P0, thr: &TMax) {
     panic!("Timeout")
 }
 
-// IDLE LOOP
-fn idle(_prio: P0, _thr: T0) -> ! {
+fn idle() -> ! {
     // OK
     rtfm::bkpt();
 
@@ -83,6 +63,3 @@ fn idle(_prio: P0, _thr: T0) -> ! {
         rtfm::wfi();
     }
 }
-
-// TASKS
-tasks!(stm32f103xx, {});
diff --git a/examples/wait1.rs b/examples/wait1.rs
index 54b6de8a9e3fc4ee03dd5a7386aa7fa5da61f969..854f466df20d705f7f389c158cdfc2d823739d9c 100644
--- a/examples/wait1.rs
+++ b/examples/wait1.rs
@@ -1,62 +1,45 @@
 //! Periodic timeouts with TIM1
 
 #![deny(warnings)]
-#![feature(const_fn)]
-#![feature(used)]
+#![feature(plugin)]
 #![no_std]
+#![plugin(cortex_m_rtfm_macros)]
 
 extern crate blue_pill;
-
-extern crate embedded_hal as hal;
-
-// version = "0.2.3"
-extern crate cortex_m_rt;
-
-// version = "0.1.0"
-#[macro_use]
 extern crate cortex_m_rtfm as rtfm;
 
+use blue_pill::Timer;
 use blue_pill::led::{self, Green};
+use blue_pill::prelude::*;
 use blue_pill::time::Hertz;
-use blue_pill::{Timer, stm32f103xx};
-use hal::prelude::*;
-use rtfm::{P0, T0, TMax};
 
 // CONFIGURATION
 const FREQUENCY: Hertz = Hertz(1);
 
-// RESOURCES
-peripherals!(stm32f103xx, {
-    GPIOC: Peripheral {
-        ceiling: C0,
-    },
-    RCC: Peripheral {
-        ceiling: C0,
-    },
-    TIM1: Peripheral {
-        ceiling: C0,
+rtfm! {
+    device: blue_pill::stm32f103xx,
+
+    init: {
+        path: init,
     },
-});
 
-// INITIALIZATION PHASE
-fn init(ref prio: P0, thr: &TMax) {
-    let gpioc = &GPIOC.access(prio, thr);
-    let rcc = &RCC.access(prio, thr);
-    let tim1 = TIM1.access(prio, thr);
+    idle: {
+        path: idle,
+        resources: [TIM1],
+    },
+}
 
-    let timer = Timer(&*tim1);
+fn init(p: init::Peripherals) {
+    let timer = Timer(p.TIM1);
 
-    led::init(gpioc, rcc);
+    led::init(p.GPIOC, p.RCC);
 
-    timer.init(FREQUENCY.invert(), rcc);
+    timer.init(FREQUENCY.invert(), p.RCC);
     timer.resume();
 }
 
-// IDLE LOOP
-fn idle(ref prio: P0, ref thr: T0) -> ! {
-    let tim1 = TIM1.access(prio, thr);
-
-    let timer = Timer(&*tim1);
+fn idle(r: idle::Resources) -> ! {
+    let timer = Timer(r.TIM1);
 
     let mut state = false;
     loop {
@@ -71,6 +54,3 @@ fn idle(ref prio: P0, ref thr: T0) -> ! {
         }
     }
 }
-
-// TASKS
-tasks!(stm32f103xx, {});
diff --git a/examples/wait2.rs b/examples/wait2.rs
index 6d881dbbca050b56896ae194afdae70a254f302c..7bbf5828febab29c515e74355e425e5acd650fc4 100644
--- a/examples/wait2.rs
+++ b/examples/wait2.rs
@@ -1,61 +1,44 @@
 //! Periodic timeouts with TIM2
 
 #![deny(warnings)]
-#![feature(const_fn)]
-#![feature(used)]
+#![feature(plugin)]
 #![no_std]
+#![plugin(cortex_m_rtfm_macros)]
 
 extern crate blue_pill;
-
-extern crate embedded_hal as hal;
-
-// version = "0.2.3"
-extern crate cortex_m_rt;
-
-// version = "0.1.0"
-#[macro_use]
 extern crate cortex_m_rtfm as rtfm;
 
+use blue_pill::Timer;
 use blue_pill::led::{self, Green};
+use blue_pill::prelude::*;
 use blue_pill::time::Hertz;
-use blue_pill::{Timer, stm32f103xx};
-use hal::prelude::*;
-use rtfm::{P0, T0, TMax};
 
 // CONFIGURATION
 const FREQUENCY: Hertz = Hertz(1);
 
-// RESOURCES
-peripherals!(stm32f103xx, {
-    GPIOC: Peripheral {
-        ceiling: C0,
-    },
-    RCC: Peripheral {
-        ceiling: C0,
-    },
-    TIM2: Peripheral {
-        ceiling: C0,
+rtfm! {
+    device: blue_pill::stm32f103xx,
+
+    init: {
+        path: init,
     },
-});
 
-// INITIALIZATION PHASE
-fn init(ref prio: P0, thr: &TMax) {
-    let gpioc = &GPIOC.access(prio, thr);
-    let rcc = &RCC.access(prio, thr);
-    let tim2 = TIM2.access(prio, thr);
+    idle: {
+        path: idle,
+        resources: [TIM2],
+    },
+}
 
-    let timer = Timer(&*tim2);
+fn init(p: init::Peripherals) {
+    let timer = Timer(p.TIM2);
 
-    led::init(gpioc, rcc);
-    timer.init(FREQUENCY.invert(), rcc);
+    led::init(p.GPIOC, p.RCC);
+    timer.init(FREQUENCY.invert(), p.RCC);
     timer.resume();
 }
 
-// IDLE LOOP
-fn idle(ref prio: P0, ref thr: T0) -> ! {
-    let tim2 = TIM2.access(prio, thr);
-
-    let timer = Timer(&*tim2);
+fn idle(r: idle::Resources) -> ! {
+    let timer = Timer(r.TIM2);
 
     let mut state = false;
     loop {
@@ -70,6 +53,3 @@ fn idle(ref prio: P0, ref thr: T0) -> ! {
         }
     }
 }
-
-// TASKS
-tasks!(stm32f103xx, {});
diff --git a/examples/wait3.rs b/examples/wait3.rs
index 2d669a07abc374dcf756d95bbe04b5bf4623e3d8..d2643a370c59b849aad14e5a73ebe2d66fcb15fc 100644
--- a/examples/wait3.rs
+++ b/examples/wait3.rs
@@ -1,62 +1,45 @@
 //! Periodic timeouts with TIM3
 
 #![deny(warnings)]
-#![feature(const_fn)]
-#![feature(used)]
+#![feature(plugin)]
 #![no_std]
+#![plugin(cortex_m_rtfm_macros)]
 
 extern crate blue_pill;
-
-extern crate embedded_hal as hal;
-
-// version = "0.2.3"
-extern crate cortex_m_rt;
-
-// version = "0.1.0"
-#[macro_use]
 extern crate cortex_m_rtfm as rtfm;
 
+use blue_pill::Timer;
 use blue_pill::led::{self, Green};
+use blue_pill::prelude::*;
 use blue_pill::time::Hertz;
-use blue_pill::{Timer, stm32f103xx};
-use hal::prelude::*;
-use rtfm::{P0, T0, TMax};
 
 // CONFIGURATION
 const FREQUENCY: Hertz = Hertz(1);
 
-// RESOURCES
-peripherals!(stm32f103xx, {
-    GPIOC: Peripheral {
-        ceiling: C0,
-    },
-    RCC: Peripheral {
-        ceiling: C0,
-    },
-    TIM3: Peripheral {
-        ceiling: C0,
+rtfm! {
+    device: blue_pill::stm32f103xx,
+
+    init: {
+        path: init,
     },
-});
 
-// INITIALIZATION PHASE
-fn init(ref prio: P0, thr: &TMax) {
-    let gpioc = &GPIOC.access(prio, thr);
-    let rcc = &RCC.access(prio, thr);
-    let tim3 = TIM3.access(prio, thr);
+    idle: {
+        path: idle,
+        resources: [TIM3],
+    },
+}
 
-    let timer = Timer(&*tim3);
+fn init(p: init::Peripherals) {
+    let timer = Timer(p.TIM3);
 
-    led::init(gpioc, rcc);
+    led::init(p.GPIOC, p.RCC);
 
-    timer.init(FREQUENCY.invert(), rcc);
+    timer.init(FREQUENCY.invert(), p.RCC);
     timer.resume();
 }
 
-// IDLE LOOP
-fn idle(ref prio: P0, ref thr: T0) -> ! {
-    let tim3 = TIM3.access(prio, thr);
-
-    let timer = Timer(&*tim3);
+fn idle(r: idle::Resources) -> ! {
+    let timer = Timer(r.TIM3);
 
     let mut state = false;
     loop {
@@ -71,6 +54,3 @@ fn idle(ref prio: P0, ref thr: T0) -> ! {
         }
     }
 }
-
-// TASKS
-tasks!(stm32f103xx, {});
diff --git a/examples/wait4.rs b/examples/wait4.rs
index c4e7e564a5a78fef0617dd1e5285f6e0c1e0edd9..df55f68f401c954cbfa630351cdfde35384def18 100644
--- a/examples/wait4.rs
+++ b/examples/wait4.rs
@@ -1,62 +1,45 @@
 //! Periodic timeouts with TIM4
 
 #![deny(warnings)]
-#![feature(const_fn)]
-#![feature(used)]
+#![feature(plugin)]
 #![no_std]
+#![plugin(cortex_m_rtfm_macros)]
 
 extern crate blue_pill;
-
-extern crate embedded_hal as hal;
-
-// version = "0.2.3"
-extern crate cortex_m_rt;
-
-// version = "0.1.0"
-#[macro_use]
 extern crate cortex_m_rtfm as rtfm;
 
+use blue_pill::Timer;
 use blue_pill::led::{self, Green};
+use blue_pill::prelude::*;
 use blue_pill::time::Hertz;
-use blue_pill::{Timer, stm32f103xx};
-use hal::prelude::*;
-use rtfm::{P0, T0, TMax};
 
 // CONFIGURATION
 const FREQUENCY: Hertz = Hertz(1);
 
-// RESOURCES
-peripherals!(stm32f103xx, {
-    GPIOC: Peripheral {
-        ceiling: C0,
-    },
-    RCC: Peripheral {
-        ceiling: C0,
-    },
-    TIM4: Peripheral {
-        ceiling: C0,
+rtfm! {
+    device: blue_pill::stm32f103xx,
+
+    init: {
+        path: init,
     },
-});
 
-// INITIALIZATION PHASE
-fn init(ref prio: P0, thr: &TMax) {
-    let gpioc = &GPIOC.access(prio, thr);
-    let rcc = &RCC.access(prio, thr);
-    let tim4 = TIM4.access(prio, thr);
+    idle: {
+        path: idle,
+        resources: [TIM4],
+    },
+}
 
-    let timer = Timer(&*tim4);
+fn init(p: init::Peripherals) {
+    let timer = Timer(p.TIM4);
 
-    led::init(gpioc, rcc);
+    led::init(p.GPIOC, p.RCC);
 
-    timer.init(FREQUENCY.invert(), rcc);
+    timer.init(FREQUENCY.invert(), p.RCC);
     timer.resume();
 }
 
-// IDLE LOOP
-fn idle(ref prio: P0, ref thr: T0) -> ! {
-    let tim4 = TIM4.access(prio, thr);
-
-    let timer = Timer(&*tim4);
+fn idle(r: idle::Resources) -> ! {
+    let timer = Timer(r.TIM4);
 
     let mut state = false;
     loop {
@@ -71,6 +54,3 @@ fn idle(ref prio: P0, ref thr: T0) -> ! {
         }
     }
 }
-
-// TASKS
-tasks!(stm32f103xx, {});
diff --git a/examples/ws2812.rs b/examples/ws2812.rs
index dfd439d189575c319af29783d6ce68a1846112d2..0d3ec896cdad3c5e821c2f78985405ff9734787c 100644
--- a/examples/ws2812.rs
+++ b/examples/ws2812.rs
@@ -4,92 +4,67 @@
 
 #![deny(warnings)]
 #![feature(const_fn)]
-#![feature(used)]
+#![feature(plugin)]
 #![no_std]
+#![plugin(cortex_m_rtfm_macros)]
 
 extern crate blue_pill;
-
-// version = "0.2.3"
-extern crate cortex_m_rt;
-
-// version = "0.1.0"
-#[macro_use]
 extern crate cortex_m_rtfm as rtfm;
-
-extern crate embedded_hal as hal;
-
 #[macro_use]
 extern crate nb;
 
 use blue_pill::dma::{Buffer, Dma1Channel2};
+use blue_pill::prelude::*;
 use blue_pill::time::Hertz;
-use blue_pill::{Channel, Pwm, stm32f103xx};
-use hal::prelude::*;
-use rtfm::{C1, P0, Resource, T0, TMax};
+use blue_pill::{Channel, Pwm};
 
 // CONFIGURATION
 const FREQUENCY: Hertz = Hertz(200_000);
 const _0: u8 = 3;
 const _1: u8 = 5;
 
-// RESOURCES
-peripherals!(stm32f103xx, {
-    AFIO: Peripheral {
-        ceiling: C0,
-    },
-    DMA1: Peripheral {
-        ceiling: C0,
-    },
-    GPIOA: Peripheral {
-        ceiling: C0,
-    },
-    RCC: Peripheral {
-        ceiling: C0,
-    },
-    TIM2: Peripheral {
-        ceiling: C0,
+rtfm! {
+    device: blue_pill::stm32f103xx,
+
+    resources: {
+        BUFFER: Buffer<[u8; 577], Dma1Channel2> = Buffer::new([_0; 577]);
     },
-});
 
-static BUFFER: Resource<Buffer<[u8; (24 * 24) + 1], Dma1Channel2>, C1> =
-    Resource::new(Buffer::new([_0; (24 * 24) + 1]));
+    init: {
+        path: init,
+    },
 
-// INITIALIZATION PHASE
-fn init(ref prio: P0, thr: &TMax) {
-    let afio = &AFIO.access(prio, thr);
-    let buffer = BUFFER.access(prio, thr);
-    let dma1 = &DMA1.access(prio, thr);
-    let gpioa = &GPIOA.access(prio, thr);
-    let rcc = &RCC.access(prio, thr);
-    let tim2 = TIM2.access(prio, thr);
+    idle: {
+        path: idle,
+        resources: [BUFFER, DMA1, TIM2],
+    },
+}
 
-    let pwm = Pwm(&*tim2);
+fn init(p: init::Peripherals, r: init::Resources) {
+    let pwm = Pwm(p.TIM2);
 
-    pwm.init(FREQUENCY.invert(), afio, Some(dma1), gpioa, rcc);
+    pwm.init(FREQUENCY.invert(), p.AFIO, Some(p.DMA1), p.GPIOA, p.RCC);
     pwm.enable(Channel::_1);
 
     // end of frame
-    *buffer.borrow_mut().last_mut().unwrap() = 0;
+    *r.BUFFER.borrow_mut().last_mut().unwrap() = 0;
 
     // set each RGB value to 0x0A0A0A
-    for byte in buffer.borrow_mut()[..(24 * 24)].chunks_mut(8) {
+    for byte in r.BUFFER.borrow_mut()[..(24 * 24)].chunks_mut(8) {
         byte.copy_from_slice(&[_0, _0, _0, _0, _1, _1, _1, _1]);
     }
+}
+
+fn idle(r: idle::Resources) -> ! {
+    let pwm = Pwm(r.TIM2);
 
-    pwm.set_duties(dma1, Channel::_1, buffer).unwrap();
+    pwm.set_duties(r.DMA1, Channel::_1, r.BUFFER).unwrap();
 
-    block!(buffer.release(dma1)).unwrap();
+    block!(r.BUFFER.release(r.DMA1)).unwrap();
 
     rtfm::bkpt();
-}
 
-// IDLE LOOP
-fn idle(_prio: P0, _thr: T0) -> ! {
-    // Sleep
     loop {
         rtfm::wfi();
     }
 }
-
-// TASKS
-tasks!(stm32f103xx, {});
diff --git a/memory.x b/memory.x
index d989f78d67665dab1bd7854b4c35d7dc49d030f0..59195b8f2e4a01fc310d82d87d24723a1eb7f40a 100644
--- a/memory.x
+++ b/memory.x
@@ -3,5 +3,3 @@ MEMORY
   FLASH : ORIGIN = 0x08000000, LENGTH = 64K
   RAM : ORIGIN = 0x20000000, LENGTH = 20K
 }
-
-_stack_start = ORIGIN(RAM) + LENGTH(RAM);
diff --git a/src/adc.rs b/src/adc.rs
index 0e16b658e24e79fc6fde3018994270911945e15e..571c5407a51b9877e80cb3cb275da6ea7f3b7773 100644
--- a/src/adc.rs
+++ b/src/adc.rs
@@ -4,7 +4,7 @@ use core::marker::Unsize;
 
 use cast::u16;
 use hal::prelude::*;
-use static_ref::Ref;
+use static_ref::Static;
 
 use dma::{self, CircBuffer, Dma1Channel1};
 use stm32f103xx::{ADC1, DMA1, GPIOA, RCC, TIM2};
@@ -51,7 +51,7 @@ impl<'a> Adc1<'a> {
         // en: Disabled
         dma1.ccr1.write(|w| unsafe {
             w.mem2mem()
-                .clear()
+                .clear_bit()
                 .pl()
                 .bits(0b01)
                 .msize()
@@ -59,19 +59,19 @@ impl<'a> Adc1<'a> {
                 .psize()
                 .bits(0b01)
                 .minc()
-                .set()
+                .set_bit()
                 .pinc()
-                .clear()
+                .clear_bit()
                 .circ()
-                .set()
+                .set_bit()
                 .dir()
-                .clear()
+                .clear_bit()
                 .htie()
-                .set()
+                .set_bit()
                 .tcie()
-                .set()
+                .set_bit()
                 .en()
-                .clear()
+                .clear_bit()
         });
 
         // exttrig: Conversion on external event enabled
@@ -82,29 +82,28 @@ impl<'a> Adc1<'a> {
         // adon: Disable ADC conversion
         adc1.cr2.write(|w| unsafe {
             w.exttrig()
-                .set()
+                .set_bit()
                 .extsel()
                 .bits(0b011) // T2C2
-                // .bits(0b111) // swstart
                 .align()
-                .clear()
+                .clear_bit()
                 .dma()
-                .set()
+                .set_bit()
                 .cont()
-                .clear()
+                .clear_bit()
                 .adon()
-                .clear()
+                .clear_bit()
         });
     }
 
     /// Disables the ADC
     pub fn disable(&self) {
-        self.0.cr2.modify(|_, w| w.adon().clear());
+        self.0.cr2.modify(|_, w| w.adon().clear_bit());
     }
 
     /// Enables the ADC
     pub fn enable(&self) {
-        self.0.cr2.modify(|_, w| w.adon().set());
+        self.0.cr2.modify(|_, w| w.adon().set_bit());
     }
 
     /// Starts an analog to digital conversion that will be periodically
@@ -113,7 +112,7 @@ impl<'a> Adc1<'a> {
     /// The conversions will be stored in the circular `buffer`
     pub fn start<B>(
         &self,
-        buffer: Ref<CircBuffer<u16, B, Dma1Channel1>>,
+        buffer: &Static<CircBuffer<B, Dma1Channel1>>,
         dma1: &DMA1,
         pwm: Pwm<TIM2>,
     ) -> Result<(), dma::Error>
@@ -122,8 +121,7 @@ impl<'a> Adc1<'a> {
     {
         let adc1 = self.0;
 
-
-        if dma1.ccr1.read().en().is_set() {
+        if dma1.ccr1.read().en().bit_is_set() {
             return Err(dma::Error::InUse);
         }
 
@@ -141,7 +139,7 @@ impl<'a> Adc1<'a> {
         dma1.cmar1
             .write(|w| unsafe { w.bits(buffer.as_ptr() as u32) });
 
-        dma1.ccr1.modify(|_, w| w.en().set());
+        dma1.ccr1.modify(|_, w| w.en().set_bit());
         pwm.enable(Channel::_2);
 
         Ok(())
diff --git a/src/capture.rs b/src/capture.rs
index 89c111ead9d1979106e43721fa9bf268e6816a3d..ef30b3693e1a3474ee15cd293ca21580c0328f48 100644
--- a/src/capture.rs
+++ b/src/capture.rs
@@ -103,9 +103,8 @@ impl<'a> Capture<'a, TIM1> {
         });
 
         // don't remap TIM1 pins
-        afio.mapr.modify(
-            |_, w| unsafe { w.tim1_remap().bits(0b00) },
-        );
+        afio.mapr
+            .modify(|_, w| unsafe { w.tim1_remap().bits(0b00) });
 
         // CH1 = PA8 = floating input
         // CH2 = PA9 = floating input
@@ -142,13 +141,13 @@ impl<'a> Capture<'a, TIM1> {
         // enable capture on rising edge
         tim1.ccer.modify(|_, w| {
             w.cc1p()
-                .clear()
+                .clear_bit()
                 .cc2p()
-                .clear()
+                .clear_bit()
                 .cc3p()
-                .clear()
+                .clear_bit()
                 .cc4p()
-                .clear()
+                .clear_bit()
         });
 
         self._set_resolution(resolution);
@@ -156,9 +155,8 @@ impl<'a> Capture<'a, TIM1> {
         tim1.arr.write(|w| w.arr().bits(u16::MAX));
 
         // configure timer as a continuous upcounter and start
-        tim1.cr1.write(
-            |w| w.dir().up().opm().continuous().cen().enabled(),
-        );
+        tim1.cr1
+            .write(|w| w.dir().up().opm().continuous().cen().enabled());
     }
 
     /// Starts listening for an interrupt `event`
@@ -166,10 +164,10 @@ impl<'a> Capture<'a, TIM1> {
         let tim1 = self.0;
 
         match event {
-            Event::Capture1 => tim1.dier.modify(|_, w| w.cc1ie().set()),
-            Event::Capture2 => tim1.dier.modify(|_, w| w.cc2ie().set()),
-            Event::Capture3 => tim1.dier.modify(|_, w| w.cc3ie().set()),
-            Event::Capture4 => tim1.dier.modify(|_, w| w.cc4ie().set()),
+            Event::Capture1 => tim1.dier.modify(|_, w| w.cc1ie().set_bit()),
+            Event::Capture2 => tim1.dier.modify(|_, w| w.cc2ie().set_bit()),
+            Event::Capture3 => tim1.dier.modify(|_, w| w.cc3ie().set_bit()),
+            Event::Capture4 => tim1.dier.modify(|_, w| w.cc4ie().set_bit()),
         }
     }
 
@@ -178,10 +176,10 @@ impl<'a> Capture<'a, TIM1> {
         let tim1 = self.0;
 
         match event {
-            Event::Capture1 => tim1.dier.modify(|_, w| w.cc1ie().clear()),
-            Event::Capture2 => tim1.dier.modify(|_, w| w.cc2ie().clear()),
-            Event::Capture3 => tim1.dier.modify(|_, w| w.cc3ie().clear()),
-            Event::Capture4 => tim1.dier.modify(|_, w| w.cc4ie().clear()),
+            Event::Capture1 => tim1.dier.modify(|_, w| w.cc1ie().clear_bit()),
+            Event::Capture2 => tim1.dier.modify(|_, w| w.cc2ie().clear_bit()),
+            Event::Capture3 => tim1.dier.modify(|_, w| w.cc3ie().clear_bit()),
+            Event::Capture4 => tim1.dier.modify(|_, w| w.cc4ie().clear_bit()),
         }
     }
 
@@ -206,36 +204,36 @@ impl<'a> hal::Capture for Capture<'a, TIM1> {
 
         match channel {
             Channel::_1 => {
-                if sr.cc1of().is_set() {
+                if sr.cc1of().bit_is_set() {
                     Err(nb::Error::Other(Error::Overcapture))
-                } else if sr.cc1if().is_set() {
+                } else if sr.cc1if().bit_is_set() {
                     Ok(tim1.ccr1.read().ccr1().bits())
                 } else {
                     Err(nb::Error::WouldBlock)
                 }
             }
             Channel::_2 => {
-                if sr.cc2of().is_set() {
+                if sr.cc2of().bit_is_set() {
                     Err(nb::Error::Other(Error::Overcapture))
-                } else if sr.cc2if().is_set() {
+                } else if sr.cc2if().bit_is_set() {
                     Ok(tim1.ccr2.read().ccr2().bits())
                 } else {
                     Err(nb::Error::WouldBlock)
                 }
             }
             Channel::_3 => {
-                if sr.cc3of().is_set() {
+                if sr.cc3of().bit_is_set() {
                     Err(nb::Error::Other(Error::Overcapture))
-                } else if sr.cc3if().is_set() {
+                } else if sr.cc3if().bit_is_set() {
                     Ok(tim1.ccr3.read().ccr3().bits())
                 } else {
                     Err(nb::Error::WouldBlock)
                 }
             }
             Channel::_4 => {
-                if sr.cc4of().is_set() {
+                if sr.cc4of().bit_is_set() {
                     Err(nb::Error::Other(Error::Overcapture))
-                } else if sr.cc4if().is_set() {
+                } else if sr.cc4if().bit_is_set() {
                     Ok(tim1.ccr4.read().ccr4().bits())
                 } else {
                     Err(nb::Error::WouldBlock)
@@ -246,19 +244,19 @@ impl<'a> hal::Capture for Capture<'a, TIM1> {
 
     fn disable(&self, channel: Channel) {
         match channel {
-            Channel::_1 => self.0.ccer.modify(|_, w| w.cc1e().clear()),
-            Channel::_2 => self.0.ccer.modify(|_, w| w.cc2e().clear()),
-            Channel::_3 => self.0.ccer.modify(|_, w| w.cc3e().clear()),
-            Channel::_4 => self.0.ccer.modify(|_, w| w.cc4e().clear()),
+            Channel::_1 => self.0.ccer.modify(|_, w| w.cc1e().clear_bit()),
+            Channel::_2 => self.0.ccer.modify(|_, w| w.cc2e().clear_bit()),
+            Channel::_3 => self.0.ccer.modify(|_, w| w.cc3e().clear_bit()),
+            Channel::_4 => self.0.ccer.modify(|_, w| w.cc4e().clear_bit()),
         }
     }
 
     fn enable(&self, channel: Channel) {
         match channel {
-            Channel::_1 => self.0.ccer.modify(|_, w| w.cc1e().set()),
-            Channel::_2 => self.0.ccer.modify(|_, w| w.cc2e().set()),
-            Channel::_3 => self.0.ccer.modify(|_, w| w.cc3e().set()),
-            Channel::_4 => self.0.ccer.modify(|_, w| w.cc4e().set()),
+            Channel::_1 => self.0.ccer.modify(|_, w| w.cc1e().set_bit()),
+            Channel::_2 => self.0.ccer.modify(|_, w| w.cc2e().set_bit()),
+            Channel::_3 => self.0.ccer.modify(|_, w| w.cc3e().set_bit()),
+            Channel::_4 => self.0.ccer.modify(|_, w| w.cc4e().set_bit()),
         }
     }
 
@@ -324,9 +322,8 @@ where
 
         // don't remap TIM pins
         if tim2.get_type_id() == TypeId::of::<TIM2>() {
-            afio.mapr.modify(
-                |_, w| unsafe { w.tim2_remap().bits(0b00) },
-            );
+            afio.mapr
+                .modify(|_, w| unsafe { w.tim2_remap().bits(0b00) });
 
             // CH1 = PA0 = floating input
             // CH2 = PA1 = floating input
@@ -351,9 +348,8 @@ where
                     .bits(0b01)
             });
         } else if tim2.get_type_id() == TypeId::of::<TIM3>() {
-            afio.mapr.modify(
-                |_, w| unsafe { w.tim3_remap().bits(0b00) },
-            );
+            afio.mapr
+                .modify(|_, w| unsafe { w.tim3_remap().bits(0b00) });
 
             // CH1 = PA6 = floating input
             // CH2 = PA7 = floating input
@@ -370,7 +366,7 @@ where
                     .bits(0b01)
             });
         } else if tim2.get_type_id() == TypeId::of::<TIM4>() {
-            afio.mapr.modify(|_, w| w.tim4_remap().clear());
+            afio.mapr.modify(|_, w| w.tim4_remap().clear_bit());
 
             // CH1 = PB6 = floating input
             // CH2 = PB7 = floating input
@@ -417,32 +413,32 @@ where
         if tim2.get_type_id() == TypeId::of::<TIM3>() {
             tim2.ccer.modify(|_, w| {
                 w.cc1p()
-                    .clear()
+                    .clear_bit()
                     .cc1e()
-                    .clear()
+                    .clear_bit()
                     .cc2p()
-                    .clear()
+                    .clear_bit()
                     .cc2e()
-                    .clear()
+                    .clear_bit()
             });
         } else {
             tim2.ccer.modify(|_, w| {
                 w.cc1p()
-                    .clear()
+                    .clear_bit()
                     .cc1e()
-                    .clear()
+                    .clear_bit()
                     .cc2p()
-                    .clear()
+                    .clear_bit()
                     .cc2e()
-                    .clear()
+                    .clear_bit()
                     .cc3p()
-                    .clear()
+                    .clear_bit()
                     .cc3e()
-                    .clear()
+                    .clear_bit()
                     .cc4p()
-                    .clear()
+                    .clear_bit()
                     .cc4e()
-                    .clear()
+                    .clear_bit()
             });
         }
 
@@ -451,9 +447,8 @@ where
         tim2.arr.write(|w| w.arr().bits(u16::MAX));
 
         // configure timer as a continuous upcounter and start
-        tim2.cr1.write(
-            |w| w.dir().up().opm().continuous().cen().enabled(),
-        );
+        tim2.cr1
+            .write(|w| w.dir().up().opm().continuous().cen().enabled());
     }
 
     /// Starts listening for an interrupt `event`
@@ -461,10 +456,10 @@ where
         let tim = self.0;
 
         match event {
-            Event::Capture1 => tim.dier.modify(|_, w| w.cc1ie().set()),
-            Event::Capture2 => tim.dier.modify(|_, w| w.cc2ie().set()),
-            Event::Capture3 => tim.dier.modify(|_, w| w.cc3ie().set()),
-            Event::Capture4 => tim.dier.modify(|_, w| w.cc4ie().set()),
+            Event::Capture1 => tim.dier.modify(|_, w| w.cc1ie().set_bit()),
+            Event::Capture2 => tim.dier.modify(|_, w| w.cc2ie().set_bit()),
+            Event::Capture3 => tim.dier.modify(|_, w| w.cc3ie().set_bit()),
+            Event::Capture4 => tim.dier.modify(|_, w| w.cc4ie().set_bit()),
         }
     }
 
@@ -473,10 +468,10 @@ where
         let tim = self.0;
 
         match event {
-            Event::Capture1 => tim.dier.modify(|_, w| w.cc1ie().clear()),
-            Event::Capture2 => tim.dier.modify(|_, w| w.cc2ie().clear()),
-            Event::Capture3 => tim.dier.modify(|_, w| w.cc3ie().clear()),
-            Event::Capture4 => tim.dier.modify(|_, w| w.cc4ie().clear()),
+            Event::Capture1 => tim.dier.modify(|_, w| w.cc1ie().clear_bit()),
+            Event::Capture2 => tim.dier.modify(|_, w| w.cc2ie().clear_bit()),
+            Event::Capture3 => tim.dier.modify(|_, w| w.cc3ie().clear_bit()),
+            Event::Capture4 => tim.dier.modify(|_, w| w.cc4ie().clear_bit()),
         }
     }
 
@@ -504,36 +499,36 @@ where
 
         match channel {
             Channel::_1 => {
-                if sr.cc1of().is_set() {
+                if sr.cc1of().bit_is_set() {
                     Err(nb::Error::Other(Error::Overcapture))
-                } else if sr.cc1if().is_set() {
+                } else if sr.cc1if().bit_is_set() {
                     Ok(tim1.ccr1.read().ccr1().bits())
                 } else {
                     Err(nb::Error::WouldBlock)
                 }
             }
             Channel::_2 => {
-                if sr.cc2of().is_set() {
+                if sr.cc2of().bit_is_set() {
                     Err(nb::Error::Other(Error::Overcapture))
-                } else if sr.cc2if().is_set() {
+                } else if sr.cc2if().bit_is_set() {
                     Ok(tim1.ccr2.read().ccr2().bits())
                 } else {
                     Err(nb::Error::WouldBlock)
                 }
             }
             Channel::_3 => {
-                if sr.cc3of().is_set() {
+                if sr.cc3of().bit_is_set() {
                     Err(nb::Error::Other(Error::Overcapture))
-                } else if sr.cc3if().is_set() {
+                } else if sr.cc3if().bit_is_set() {
                     Ok(tim1.ccr3.read().ccr3().bits())
                 } else {
                     Err(nb::Error::WouldBlock)
                 }
             }
             Channel::_4 => {
-                if sr.cc4of().is_set() {
+                if sr.cc4of().bit_is_set() {
                     Err(nb::Error::Other(Error::Overcapture))
-                } else if sr.cc4if().is_set() {
+                } else if sr.cc4if().bit_is_set() {
                     Ok(tim1.ccr4.read().ccr4().bits())
                 } else {
                     Err(nb::Error::WouldBlock)
@@ -544,19 +539,19 @@ where
 
     fn disable(&self, channel: Channel) {
         match channel {
-            Channel::_1 => self.0.ccer.modify(|_, w| w.cc1e().clear()),
-            Channel::_2 => self.0.ccer.modify(|_, w| w.cc2e().clear()),
-            Channel::_3 => self.0.ccer.modify(|_, w| w.cc3e().clear()),
-            Channel::_4 => self.0.ccer.modify(|_, w| w.cc4e().clear()),
+            Channel::_1 => self.0.ccer.modify(|_, w| w.cc1e().clear_bit()),
+            Channel::_2 => self.0.ccer.modify(|_, w| w.cc2e().clear_bit()),
+            Channel::_3 => self.0.ccer.modify(|_, w| w.cc3e().clear_bit()),
+            Channel::_4 => self.0.ccer.modify(|_, w| w.cc4e().clear_bit()),
         }
     }
 
     fn enable(&self, channel: Channel) {
         match channel {
-            Channel::_1 => self.0.ccer.modify(|_, w| w.cc1e().set()),
-            Channel::_2 => self.0.ccer.modify(|_, w| w.cc2e().set()),
-            Channel::_3 => self.0.ccer.modify(|_, w| w.cc3e().set()),
-            Channel::_4 => self.0.ccer.modify(|_, w| w.cc4e().set()),
+            Channel::_1 => self.0.ccer.modify(|_, w| w.cc1e().set_bit()),
+            Channel::_2 => self.0.ccer.modify(|_, w| w.cc2e().set_bit()),
+            Channel::_3 => self.0.ccer.modify(|_, w| w.cc3e().set_bit()),
+            Channel::_4 => self.0.ccer.modify(|_, w| w.cc4e().set_bit()),
         }
     }
 
diff --git a/src/dma.rs b/src/dma.rs
index d4f6f31773c6a186c804bb11372f378024bee0b3..2aa1edc734c350f0b26fba4d72e4eaff23e4b3c8 100644
--- a/src/dma.rs
+++ b/src/dma.rs
@@ -1,12 +1,11 @@
 //! Direct Memory Access (DMA)
 
 use core::cell::{Cell, UnsafeCell};
-use core::marker::{PhantomData, Unsize};
-use core::{ops, slice};
+use core::marker::PhantomData;
+use core::ops;
 
 use nb;
 use stm32f103xx::DMA1;
-use volatile_register::RO;
 
 /// DMA error
 #[derive(Debug)]
@@ -202,12 +201,12 @@ impl<T> Buffer<T, Dma1Channel2> {
             return Ok(());
         }
 
-        if dma1.isr.read().teif2().is_set() {
+        if dma1.isr.read().teif2().bit_is_set() {
             Err(nb::Error::Other(Error::Transfer))
-        } else if dma1.isr.read().tcif2().is_set() {
+        } else if dma1.isr.read().tcif2().bit_is_set() {
             unsafe { self.unlock(status) }
-            dma1.ifcr.write(|w| w.ctcif2().set());
-            dma1.ccr2.modify(|_, w| w.en().clear());
+            dma1.ifcr.write(|w| w.ctcif2().set_bit());
+            dma1.ccr2.modify(|_, w| w.en().clear_bit());
             Ok(())
         } else {
             Err(nb::Error::WouldBlock)
@@ -224,12 +223,12 @@ impl<T> Buffer<T, Dma1Channel4> {
             return Ok(());
         }
 
-        if dma1.isr.read().teif4().is_set() {
+        if dma1.isr.read().teif4().bit_is_set() {
             Err(nb::Error::Other(Error::Transfer))
-        } else if dma1.isr.read().tcif4().is_set() {
+        } else if dma1.isr.read().tcif4().bit_is_set() {
             unsafe { self.unlock(status) }
-            dma1.ifcr.write(|w| w.ctcif4().set());
-            dma1.ccr4.modify(|_, w| w.en().clear());
+            dma1.ifcr.write(|w| w.ctcif4().set_bit());
+            dma1.ccr4.modify(|_, w| w.en().clear_bit());
             Ok(())
         } else {
             Err(nb::Error::WouldBlock)
@@ -246,12 +245,12 @@ impl<T> Buffer<T, Dma1Channel5> {
             return Ok(());
         }
 
-        if dma1.isr.read().teif5().is_set() {
+        if dma1.isr.read().teif5().bit_is_set() {
             Err(nb::Error::Other(Error::Transfer))
-        } else if dma1.isr.read().tcif5().is_set() {
+        } else if dma1.isr.read().tcif5().bit_is_set() {
             unsafe { self.unlock(status) }
-            dma1.ifcr.write(|w| w.ctcif5().set());
-            dma1.ccr5.modify(|_, w| w.en().clear());
+            dma1.ifcr.write(|w| w.ctcif5().set_bit());
+            dma1.ccr5.modify(|_, w| w.en().clear_bit());
             Ok(())
         } else {
             Err(nb::Error::WouldBlock)
@@ -260,20 +259,13 @@ impl<T> Buffer<T, Dma1Channel5> {
 }
 
 /// A circular buffer associated to a DMA `CHANNEL`
-pub struct CircBuffer<T, B, CHANNEL>
-where
-    B: Unsize<[T]>,
-{
+pub struct CircBuffer<B, CHANNEL> {
     _marker: PhantomData<CHANNEL>,
-    _t: PhantomData<[T]>,
     buffer: UnsafeCell<[B; 2]>,
     status: Cell<CircStatus>,
 }
 
-impl<T, B, CHANNEL> CircBuffer<T, B, CHANNEL>
-where
-    B: Unsize<[T]>,
-{
+impl<B, CHANNEL> CircBuffer<B, CHANNEL> {
     pub(crate) fn lock(&self) -> &[B; 2] {
         assert_eq!(self.status.get(), CircStatus::Free);
 
@@ -293,15 +285,10 @@ enum CircStatus {
     MutatingSecondHalf,
 }
 
-impl<T, B> CircBuffer<T, B, Dma1Channel1>
-where
-    B: Unsize<[T]>,
-    T: Atomic,
-{
+impl<B> CircBuffer<B, Dma1Channel1> {
     /// Constructs a circular buffer from two halves
     pub const fn new(buffer: [B; 2]) -> Self {
         CircBuffer {
-            _t: PhantomData,
             _marker: PhantomData,
             buffer: UnsafeCell::new(buffer),
             status: Cell::new(CircStatus::Free),
@@ -310,50 +297,53 @@ where
 
     /// Yields read access to the half of the circular buffer that's not
     /// currently being mutated by the DMA
-    pub fn read(&self, dma1: &DMA1) -> nb::Result<&[RO<T>], Error> {
+    pub fn read<R, F>(&self, dma1: &DMA1, f: F) -> nb::Result<R, Error>
+    where
+        F: FnOnce(&B) -> R,
+    {
         let status = self.status.get();
 
         assert_ne!(status, CircStatus::Free);
 
         let isr = dma1.isr.read();
 
-        if isr.teif1().is_set() {
+        if isr.teif1().bit_is_set() {
             Err(nb::Error::Other(Error::Transfer))
         } else {
             match status {
                 CircStatus::MutatingFirstHalf => {
-                    if isr.tcif1().is_set() {
+                    if isr.tcif1().bit_is_set() {
                         Err(nb::Error::Other(Error::Overrun))
-                    } else if isr.htif1().is_set() {
-                        dma1.ifcr.write(|w| w.chtif1().set());
+                    } else if isr.htif1().bit_is_set() {
+                        dma1.ifcr.write(|w| w.chtif1().set_bit());
 
                         self.status.set(CircStatus::MutatingSecondHalf);
 
-                        unsafe {
-                            let half: &[T] = &(*self.buffer.get())[0];
-                            Ok(slice::from_raw_parts(
-                                half.as_ptr() as *const _,
-                                half.len(),
-                            ))
+                        let ret = f(unsafe { &(*self.buffer.get())[0] });
+
+                        if isr.tcif1().bit_is_set() {
+                            Err(nb::Error::Other(Error::Overrun))
+                        } else {
+                            Ok(ret)
                         }
                     } else {
                         Err(nb::Error::WouldBlock)
                     }
                 }
                 CircStatus::MutatingSecondHalf => {
-                    if isr.htif1().is_set() {
+                    if isr.htif1().bit_is_set() {
                         Err(nb::Error::Other(Error::Overrun))
-                    } else if isr.tcif1().is_set() {
-                        dma1.ifcr.write(|w| w.ctcif1().set());
+                    } else if isr.tcif1().bit_is_set() {
+                        dma1.ifcr.write(|w| w.ctcif1().set_bit());
 
                         self.status.set(CircStatus::MutatingFirstHalf);
 
-                        unsafe {
-                            let half: &[T] = &(*self.buffer.get())[1];
-                            Ok(slice::from_raw_parts(
-                                half.as_ptr() as *const _,
-                                half.len(),
-                            ))
+                        let ret = f(unsafe { &(*self.buffer.get())[1] });
+
+                        if isr.htif1().bit_is_set() {
+                            Err(nb::Error::Other(Error::Overrun))
+                        } else {
+                            Ok(ret)
                         }
                     } else {
                         Err(nb::Error::WouldBlock)
@@ -364,10 +354,3 @@ where
         }
     }
 }
-
-/// Values that can be atomically read
-pub trait Atomic: Copy {}
-
-impl Atomic for u8 {}
-impl Atomic for u16 {}
-impl Atomic for u32 {}
diff --git a/src/lib.rs b/src/lib.rs
index fd8c0a7aafe38ce6d4aa513c2090840b77bcc376..83a783225ce7cb3a66b30d6f6244bd807927cd0f 100644
--- a/src/lib.rs
+++ b/src/lib.rs
@@ -38,6 +38,7 @@ pub mod serial;
 pub mod spi;
 pub mod time;
 pub mod timer;
+pub use hal::prelude;
 
 pub use capture::Capture;
 pub use pwm::Pwm;
diff --git a/src/pwm.rs b/src/pwm.rs
index 4d48d7eb92b1092576c4397c139ee631b4ef97f8..54d87ee064a9511b3b9982e2bd4e472082e08071 100644
--- a/src/pwm.rs
+++ b/src/pwm.rs
@@ -35,7 +35,7 @@ use core::marker::Unsize;
 
 use cast::{u16, u32};
 use hal;
-use static_ref::Ref;
+use static_ref::Static;
 use stm32f103xx::{AFIO, DMA1, GPIOA, RCC, TIM1, TIM2, TIM3, TIM4};
 
 use dma::{self, Buffer, Dma1Channel2};
@@ -70,9 +70,8 @@ impl<'a> Pwm<'a, TIM1> {
         });
 
         // no remap of TIM1 pins
-        afio.mapr.modify(
-            |_, w| unsafe { w.tim1_remap().bits(0b00) },
-        );
+        afio.mapr
+            .modify(|_, w| unsafe { w.tim1_remap().bits(0b00) });
 
         // CH1 = PA8 = alternate push-pull
         // CH2 = PA9 = alternate push-pull
@@ -99,20 +98,34 @@ impl<'a> Pwm<'a, TIM1> {
 
         // PWM mode 1
         tim1.ccmr1_output.modify(|_, w| {
-            w.oc1pe().set().oc1m().pwm1().oc2pe().set().oc2m().pwm1()
+            w.oc1pe()
+                .set_bit()
+                .oc1m()
+                .pwm1()
+                .oc2pe()
+                .set_bit()
+                .oc2m()
+                .pwm1()
         });
         tim1.ccmr2_output.modify(|_, w| {
-            w.oc3pe().set().oc3m().pwm1().oc4pe().set().oc4m().pwm1()
+            w.oc3pe()
+                .set_bit()
+                .oc3m()
+                .pwm1()
+                .oc4pe()
+                .set_bit()
+                .oc4m()
+                .pwm1()
         });
         tim1.ccer.modify(|_, w| {
             w.cc1p()
-                .clear()
+                .clear_bit()
                 .cc2p()
-                .clear()
+                .clear_bit()
                 .cc3p()
-                .clear()
+                .clear_bit()
                 .cc4p()
-                .clear()
+                .clear_bit()
         });
 
         self._set_period(period);
@@ -147,19 +160,19 @@ impl<'a> hal::Pwm for Pwm<'a, TIM1> {
 
     fn disable(&self, channel: Channel) {
         match channel {
-            Channel::_1 => self.0.ccer.modify(|_, w| w.cc1e().clear()),
-            Channel::_2 => self.0.ccer.modify(|_, w| w.cc2e().clear()),
-            Channel::_3 => self.0.ccer.modify(|_, w| w.cc3e().clear()),
-            Channel::_4 => self.0.ccer.modify(|_, w| w.cc4e().clear()),
+            Channel::_1 => self.0.ccer.modify(|_, w| w.cc1e().clear_bit()),
+            Channel::_2 => self.0.ccer.modify(|_, w| w.cc2e().clear_bit()),
+            Channel::_3 => self.0.ccer.modify(|_, w| w.cc3e().clear_bit()),
+            Channel::_4 => self.0.ccer.modify(|_, w| w.cc4e().clear_bit()),
         }
     }
 
     fn enable(&self, channel: Channel) {
         match channel {
-            Channel::_1 => self.0.ccer.modify(|_, w| w.cc1e().set()),
-            Channel::_2 => self.0.ccer.modify(|_, w| w.cc2e().set()),
-            Channel::_3 => self.0.ccer.modify(|_, w| w.cc3e().set()),
-            Channel::_4 => self.0.ccer.modify(|_, w| w.cc4e().set()),
+            Channel::_1 => self.0.ccer.modify(|_, w| w.cc1e().set_bit()),
+            Channel::_2 => self.0.ccer.modify(|_, w| w.cc2e().set_bit()),
+            Channel::_3 => self.0.ccer.modify(|_, w| w.cc3e().set_bit()),
+            Channel::_4 => self.0.ccer.modify(|_, w| w.cc4e().set_bit()),
         }
     }
 
@@ -253,9 +266,8 @@ where
         });
 
         if tim2.get_type_id() == TypeId::of::<TIM2>() {
-            afio.mapr.modify(
-                |_, w| unsafe { w.tim2_remap().bits(0b00) },
-            );
+            afio.mapr
+                .modify(|_, w| unsafe { w.tim2_remap().bits(0b00) });
 
             // CH1 = PA0 = alternate push-pull
             // CH2 = PA1 = alternate push-pull
@@ -280,9 +292,8 @@ where
                     .alt_push()
             });
         } else if tim2.get_type_id() == TypeId::of::<TIM3>() {
-            afio.mapr.modify(
-                |_, w| unsafe { w.tim3_remap().bits(0b00) },
-            );
+            afio.mapr
+                .modify(|_, w| unsafe { w.tim3_remap().bits(0b00) });
 
             // CH1 = PA6 = alternate push-pull
             // CH2 = PA7 = alternate push-pull
@@ -299,7 +310,7 @@ where
                     .alt_push()
             });
         } else if tim2.get_type_id() == TypeId::of::<TIM4>() {
-            afio.mapr.modify(|_, w| w.tim4_remap().clear());
+            afio.mapr.modify(|_, w| w.tim4_remap().clear_bit());
 
             // CH1 = PB6 = alternate push-pull
             // CH2 = PB7 = alternate push-pull
@@ -332,55 +343,56 @@ where
         if tim2.get_type_id() == TypeId::of::<TIM3>() {
             tim2.ccmr1_output.modify(|_, w| unsafe {
                 w.oc1pe()
-                    .set()
+                    .set_bit()
                     .oc1m()
                     .bits(0b110)
                     .oc2pe()
-                    .set()
+                    .set_bit()
                     .oc2m()
                     .bits(0b110)
             });
 
-            tim2.ccer.modify(|_, w| w.cc1p().clear().cc2p().clear());
+            tim2.ccer
+                .modify(|_, w| w.cc1p().clear_bit().cc2p().clear_bit());
         } else {
             tim2.ccmr1_output.modify(|_, w| unsafe {
                 w.oc1pe()
-                    .set()
+                    .set_bit()
                     .oc1m()
                     .bits(0b110)
                     .oc2pe()
-                    .set()
+                    .set_bit()
                     .oc2m()
                     .bits(0b110)
             });
 
             tim2.ccmr2_output.modify(|_, w| unsafe {
                 w.oc3pe()
-                    .set()
+                    .set_bit()
                     .oc3m()
                     .bits(0b110)
                     .oc4pe()
-                    .set()
+                    .set_bit()
                     .oc4m()
                     .bits(0b110)
             });
 
             tim2.ccer.modify(|_, w| {
                 w.cc1p()
-                    .clear()
+                    .clear_bit()
                     .cc2p()
-                    .clear()
+                    .clear_bit()
                     .cc3p()
-                    .clear()
+                    .clear_bit()
                     .cc4p()
-                    .clear()
+                    .clear_bit()
             });
         }
 
         self._set_period(period);
 
         if let Some(dma1) = dma1 {
-            tim2.dier.modify(|_, w| w.ude().set());
+            tim2.dier.modify(|_, w| w.ude().set_bit());
 
             if tim2.get_type_id() == TypeId::of::<TIM2>() {
                 // TIM2_UP
@@ -396,7 +408,7 @@ where
                 // en: Disabled
                 dma1.ccr2.write(|w| unsafe {
                     w.mem2mem()
-                        .clear()
+                        .clear_bit()
                         .pl()
                         .bits(0b01)
                         .msize()
@@ -404,17 +416,17 @@ where
                         .psize()
                         .bits(0b01)
                         .minc()
-                        .set()
+                        .set_bit()
                         .pinc()
-                        .clear()
+                        .clear_bit()
                         .circ()
-                        .clear()
+                        .clear_bit()
                         .dir()
-                        .set()
+                        .set_bit()
                         .tcie()
-                        .set()
+                        .set_bit()
                         .en()
-                        .clear()
+                        .clear_bit()
                 });
             } else {
                 unimplemented!()
@@ -448,7 +460,7 @@ where
         &self,
         dma1: &DMA1,
         channel: Channel,
-        buffer: Ref<Buffer<B, Dma1Channel2>>,
+        buffer: &Static<Buffer<B, Dma1Channel2>>,
     ) -> ::core::result::Result<(), dma::Error>
     where
         B: Unsize<[u8]>,
@@ -456,15 +468,14 @@ where
         let tim2 = self.0;
 
         if tim2.get_type_id() == TypeId::of::<TIM2>() {
-            if dma1.ccr2.read().en().is_set() {
+            if dma1.ccr2.read().en().bit_is_set() {
                 return Err(dma::Error::InUse);
             }
 
             let buffer: &[u8] = buffer.lock();
 
-            dma1.cndtr2.write(|w| unsafe {
-                w.ndt().bits(u16(buffer.len()).unwrap())
-            });
+            dma1.cndtr2
+                .write(|w| unsafe { w.ndt().bits(u16(buffer.len()).unwrap()) });
             dma1.cpar2.write(|w| unsafe {
                 match channel {
                     Channel::_1 => w.bits(&tim2.ccr1 as *const _ as u32),
@@ -473,10 +484,9 @@ where
                     Channel::_4 => w.bits(&tim2.ccr4 as *const _ as u32),
                 }
             });
-            dma1.cmar2.write(
-                |w| unsafe { w.bits(buffer.as_ptr() as u32) },
-            );
-            dma1.ccr2.modify(|_, w| w.en().set());
+            dma1.cmar2
+                .write(|w| unsafe { w.bits(buffer.as_ptr() as u32) });
+            dma1.ccr2.modify(|_, w| w.en().set_bit());
 
             Ok(())
 
@@ -505,19 +515,19 @@ where
 
     fn disable(&self, channel: Channel) {
         match channel {
-            Channel::_1 => self.0.ccer.modify(|_, w| w.cc1e().clear()),
-            Channel::_2 => self.0.ccer.modify(|_, w| w.cc2e().clear()),
-            Channel::_3 => self.0.ccer.modify(|_, w| w.cc3e().clear()),
-            Channel::_4 => self.0.ccer.modify(|_, w| w.cc4e().clear()),
+            Channel::_1 => self.0.ccer.modify(|_, w| w.cc1e().clear_bit()),
+            Channel::_2 => self.0.ccer.modify(|_, w| w.cc2e().clear_bit()),
+            Channel::_3 => self.0.ccer.modify(|_, w| w.cc3e().clear_bit()),
+            Channel::_4 => self.0.ccer.modify(|_, w| w.cc4e().clear_bit()),
         }
     }
 
     fn enable(&self, channel: Channel) {
         match channel {
-            Channel::_1 => self.0.ccer.modify(|_, w| w.cc1e().set()),
-            Channel::_2 => self.0.ccer.modify(|_, w| w.cc2e().set()),
-            Channel::_3 => self.0.ccer.modify(|_, w| w.cc3e().set()),
-            Channel::_4 => self.0.ccer.modify(|_, w| w.cc4e().set()),
+            Channel::_1 => self.0.ccer.modify(|_, w| w.cc1e().set_bit()),
+            Channel::_2 => self.0.ccer.modify(|_, w| w.cc2e().set_bit()),
+            Channel::_3 => self.0.ccer.modify(|_, w| w.cc3e().set_bit()),
+            Channel::_4 => self.0.ccer.modify(|_, w| w.cc4e().set_bit()),
         }
     }
 
diff --git a/src/qei.rs b/src/qei.rs
index 95bb17ae8069c0bee512874df07381493c59a624..6281bbcefa9d394667fae6629db10b5d68cd6680 100644
--- a/src/qei.rs
+++ b/src/qei.rs
@@ -50,14 +50,12 @@ impl<'a> Qei<'a, TIM1> {
         rcc.apb2enr.modify(|_, w| w.tim1en().enabled());
 
         // enable GPIO and AFIO
-        rcc.apb2enr.modify(
-            |_, w| w.iopaen().enabled().afioen().enabled(),
-        );
+        rcc.apb2enr
+            .modify(|_, w| w.iopaen().enabled().afioen().enabled());
 
         // no remap of TIM1 pins
-        afio.mapr.modify(
-            |_, w| unsafe { w.tim1_remap().bits(0b00) },
-        );
+        afio.mapr
+            .modify(|_, w| unsafe { w.tim1_remap().bits(0b00) });
 
         // CH1 = PA8 = floating input
         // CH2 = PA9 = floating input
@@ -73,15 +71,19 @@ impl<'a> Qei<'a, TIM1> {
         });
 
         // Configure TxC1 and TxC2 as captures
-        tim1.ccmr1_output.write(|w| unsafe {
-            w.bits({
-                (0b01 << 0) | (0b01 << 8)
-            })
-        });
+        tim1.ccmr1_output
+            .write(|w| unsafe { w.bits({ (0b01 << 0) | (0b01 << 8) }) });
 
         // enable and configure to capture on rising edge
         tim1.ccer.write(|w| {
-            w.cc1e().set().cc1p().clear().cc2e().set().cc2p().clear()
+            w.cc1e()
+                .set_bit()
+                .cc1p()
+                .clear_bit()
+                .cc2e()
+                .set_bit()
+                .cc2p()
+                .clear_bit()
         });
 
         // configure as quadrature encoder
@@ -100,7 +102,7 @@ impl<'a> hal::Qei for Qei<'a, TIM1> {
     }
 
     fn direction(&self) -> hal::Direction {
-        if self.0.cr1.read().dir().is_clear() {
+        if self.0.cr1.read().dir().bit_is_clear() {
             hal::Direction::Upcounting
         } else {
             hal::Direction::Downcounting
@@ -140,9 +142,8 @@ where
 
         // don't remap TIM pins
         if tim2.get_type_id() == TypeId::of::<TIM2>() {
-            afio.mapr.modify(
-                |_, w| unsafe { w.tim2_remap().bits(0b00) },
-            );
+            afio.mapr
+                .modify(|_, w| unsafe { w.tim2_remap().bits(0b00) });
 
             // CH1 = PA0 = floating input
             // CH2 = PA1 = floating input
@@ -157,9 +158,8 @@ where
                     .bits(0b01)
             });
         } else if tim2.get_type_id() == TypeId::of::<TIM3>() {
-            afio.mapr.modify(
-                |_, w| unsafe { w.tim3_remap().bits(0b00) },
-            );
+            afio.mapr
+                .modify(|_, w| unsafe { w.tim3_remap().bits(0b00) });
 
             // CH1 = PA6 = floating input
             // CH2 = PA7 = floating input
@@ -174,7 +174,7 @@ where
                     .bits(0b01)
             });
         } else if tim2.get_type_id() == TypeId::of::<TIM4>() {
-            afio.mapr.modify(|_, w| w.tim4_remap().clear());
+            afio.mapr.modify(|_, w| w.tim4_remap().clear_bit());
 
             // CH1 = PB6 = floating input
             // CH2 = PB7 = floating input
@@ -191,15 +191,19 @@ where
         }
 
         // Configure TxC1 and TxC2 as captures
-        tim2.ccmr1_output.write(|w| unsafe {
-            w.bits({
-                (0b01 << 0) | (0b01 << 8)
-            })
-        });
+        tim2.ccmr1_output
+            .write(|w| unsafe { w.bits({ (0b01 << 0) | (0b01 << 8) }) });
 
         // enable and configure to capture on rising edge
         tim2.ccer.write(|w| {
-            w.cc1e().set().cc1p().clear().cc2e().set().cc2p().clear()
+            w.cc1e()
+                .set_bit()
+                .cc1p()
+                .clear_bit()
+                .cc2e()
+                .set_bit()
+                .cc2p()
+                .clear_bit()
         });
 
         // configure as quadrature encoder
@@ -221,7 +225,7 @@ where
     }
 
     fn direction(&self) -> hal::Direction {
-        if self.0.cr1.read().dir().is_clear() {
+        if self.0.cr1.read().dir().bit_is_clear() {
             hal::Direction::Upcounting
         } else {
             hal::Direction::Downcounting
diff --git a/src/serial.rs b/src/serial.rs
index 1e5842a918f13ec9a3e1479e54e992454617c915..baffdf67c23777d33d4733a590e54432cfa628bd 100644
--- a/src/serial.rs
+++ b/src/serial.rs
@@ -28,7 +28,7 @@ use core::ptr;
 use cast::u16;
 use hal;
 use nb;
-use static_ref::Ref;
+use static_ref::Static;
 use stm32f103xx::{AFIO, DMA1, GPIOA, GPIOB, RCC, USART1, USART2, USART3,
                   gpioa, usart1};
 
@@ -149,19 +149,17 @@ where
             });
         } else if usart.get_type_id() == TypeId::of::<USART2>() {
             rcc.apb1enr.modify(|_, w| w.usart2en().enabled());
-            rcc.apb2enr.modify(
-                |_, w| w.afioen().enabled().iopaen().enabled(),
-            );
+            rcc.apb2enr
+                .modify(|_, w| w.afioen().enabled().iopaen().enabled());
         } else if usart.get_type_id() == TypeId::of::<USART3>() {
             rcc.apb1enr.modify(|_, w| w.usart3en().enabled());
-            rcc.apb2enr.modify(
-                |_, w| w.afioen().enabled().iopben().enabled(),
-            );
+            rcc.apb2enr
+                .modify(|_, w| w.afioen().enabled().iopben().enabled());
         }
 
         if usart.get_type_id() == TypeId::of::<USART1>() {
             // PA9 = TX, PA10 = RX
-            afio.mapr.modify(|_, w| w.usart1_remap().clear());
+            afio.mapr.modify(|_, w| w.usart1_remap().clear_bit());
             gpio.crh.modify(|_, w| {
                 w.mode9()
                     .output()
@@ -174,7 +172,7 @@ where
             });
         } else if usart.get_type_id() == TypeId::of::<USART2>() {
             // PA2 = TX, PA3 = RX
-            afio.mapr.modify(|_, w| w.usart2_remap().clear());
+            afio.mapr.modify(|_, w| w.usart2_remap().clear_bit());
             gpio.crl.modify(|_, w| {
                 w.mode2()
                     .output()
@@ -187,9 +185,8 @@ where
             });
         } else if usart.get_type_id() == TypeId::of::<USART3>() {
             // PB10 = TX, PB11 = RX
-            afio.mapr.modify(
-                |_, w| unsafe { w.usart3_remap().bits(0b00) },
-            );
+            afio.mapr
+                .modify(|_, w| unsafe { w.usart3_remap().bits(0b00) });
             gpio.crh.modify(|_, w| {
                 w.mode10()
                     .output()
@@ -217,7 +214,7 @@ where
                 // en: Disabled
                 dma1.ccr4.write(|w| unsafe {
                     w.mem2mem()
-                        .clear()
+                        .clear_bit()
                         .pl()
                         .bits(0b01)
                         .msize()
@@ -225,17 +222,17 @@ where
                         .psize()
                         .bits(0b00)
                         .minc()
-                        .set()
+                        .set_bit()
                         .circ()
-                        .clear()
+                        .clear_bit()
                         .pinc()
-                        .clear()
+                        .clear_bit()
                         .dir()
-                        .set()
+                        .set_bit()
                         .tcie()
-                        .set()
+                        .set_bit()
                         .en()
-                        .clear()
+                        .clear_bit()
                 });
 
                 // RX DMA transfer
@@ -251,7 +248,7 @@ where
                 // en: Disabled
                 dma1.ccr5.write(|w| unsafe {
                     w.mem2mem()
-                        .clear()
+                        .clear_bit()
                         .pl()
                         .bits(0b01)
                         .msize()
@@ -259,17 +256,17 @@ where
                         .psize()
                         .bits(0b00)
                         .minc()
-                        .set()
+                        .set_bit()
                         .circ()
-                        .clear()
+                        .clear_bit()
                         .pinc()
-                        .clear()
+                        .clear_bit()
                         .dir()
-                        .clear()
+                        .clear_bit()
                         .tcie()
-                        .set()
+                        .set_bit()
                         .en()
-                        .clear()
+                        .clear_bit()
                 });
             } else {
                 // TODO enable DMA for USART{2,3}
@@ -290,23 +287,30 @@ where
         // disable hardware flow control
         // enable DMA TX and RX transfers
         usart.cr3.write(|w| {
-            w.rtse().clear().ctse().clear().dmat().set().dmar().set()
+            w.rtse()
+                .clear_bit()
+                .ctse()
+                .clear_bit()
+                .dmat()
+                .set_bit()
+                .dmar()
+                .set_bit()
         });
 
         // enable TX, RX; disable parity checking
         usart.cr1.write(|w| {
             w.ue()
-                .set()
+                .set_bit()
                 .re()
-                .set()
+                .set_bit()
                 .te()
-                .set()
+                .set_bit()
                 .m()
-                .clear()
+                .clear_bit()
                 .pce()
-                .clear()
+                .clear_bit()
                 .rxneie()
-                .clear()
+                .clear_bit()
         });
     }
 
@@ -315,9 +319,9 @@ where
         let usart = self.0;
 
         match event {
-            Event::Rxne => usart.cr1.modify(|_, w| w.rxneie().set()),
-            Event::Tc => usart.cr1.modify(|_, w| w.tcie().set()),
-            Event::Txe => usart.cr1.modify(|_, w| w.txeie().set()),
+            Event::Rxne => usart.cr1.modify(|_, w| w.rxneie().set_bit()),
+            Event::Tc => usart.cr1.modify(|_, w| w.tcie().set_bit()),
+            Event::Txe => usart.cr1.modify(|_, w| w.txeie().set_bit()),
         }
     }
 
@@ -326,9 +330,9 @@ where
         let usart = self.0;
 
         match event {
-            Event::Rxne => usart.cr1.modify(|_, w| w.rxneie().clear()),
-            Event::Tc => usart.cr1.modify(|_, w| w.tcie().clear()),
-            Event::Txe => usart.cr1.modify(|_, w| w.txeie().clear()),
+            Event::Rxne => usart.cr1.modify(|_, w| w.rxneie().clear_bit()),
+            Event::Tc => usart.cr1.modify(|_, w| w.tcie().clear_bit()),
+            Event::Txe => usart.cr1.modify(|_, w| w.txeie().clear_bit()),
         }
     }
 }
@@ -343,13 +347,13 @@ where
         let usart1 = self.0;
         let sr = usart1.sr.read();
 
-        if sr.ore().is_set() {
+        if sr.ore().bit_is_set() {
             Err(nb::Error::Other(Error::Overrun))
-        } else if sr.ne().is_set() {
+        } else if sr.ne().bit_is_set() {
             Err(nb::Error::Other(Error::Noise))
-        } else if sr.fe().is_set() {
+        } else if sr.fe().bit_is_set() {
             Err(nb::Error::Other(Error::Framing))
-        } else if sr.rxne().is_set() {
+        } else if sr.rxne().bit_is_set() {
             // NOTE(read_volatile) the register is 9 bits big but we'll only
             // work with the first 8 bits
             Ok(unsafe {
@@ -364,13 +368,13 @@ where
         let usart1 = self.0;
         let sr = usart1.sr.read();
 
-        if sr.ore().is_set() {
+        if sr.ore().bit_is_set() {
             Err(nb::Error::Other(Error::Overrun))
-        } else if sr.ne().is_set() {
+        } else if sr.ne().bit_is_set() {
             Err(nb::Error::Other(Error::Noise))
-        } else if sr.fe().is_set() {
+        } else if sr.fe().bit_is_set() {
             Err(nb::Error::Other(Error::Framing))
-        } else if sr.txe().is_set() {
+        } else if sr.txe().bit_is_set() {
             // NOTE(write_volatile) see NOTE in the `read` method
             unsafe {
                 ptr::write_volatile(&usart1.dr as *const _ as *mut u8, byte)
@@ -392,29 +396,26 @@ impl<'a> Serial<'a, USART1> {
     pub fn read_exact<B>(
         &self,
         dma1: &DMA1,
-        buffer: Ref<Buffer<B, Dma1Channel5>>,
+        buffer: &Static<Buffer<B, Dma1Channel5>>,
     ) -> ::core::result::Result<(), dma::Error>
     where
         B: Unsize<[u8]>,
     {
         let usart1 = self.0;
 
-        if dma1.ccr5.read().en().is_set() {
+        if dma1.ccr5.read().en().bit_is_set() {
             return Err(dma::Error::InUse);
         }
 
         let buffer: &mut [u8] = buffer.lock_mut();
 
-        dma1.cndtr5.write(|w| unsafe {
-            w.ndt().bits(u16(buffer.len()).unwrap())
-        });
-        dma1.cpar5.write(|w| unsafe {
-            w.bits(&usart1.dr as *const _ as u32)
-        });
-        dma1.cmar5.write(
-            |w| unsafe { w.bits(buffer.as_ptr() as u32) },
-        );
-        dma1.ccr5.modify(|_, w| w.en().set());
+        dma1.cndtr5
+            .write(|w| unsafe { w.ndt().bits(u16(buffer.len()).unwrap()) });
+        dma1.cpar5
+            .write(|w| unsafe { w.bits(&usart1.dr as *const _ as u32) });
+        dma1.cmar5
+            .write(|w| unsafe { w.bits(buffer.as_ptr() as u32) });
+        dma1.ccr5.modify(|_, w| w.en().set_bit());
 
         Ok(())
     }
@@ -426,29 +427,26 @@ impl<'a> Serial<'a, USART1> {
     pub fn write_all<B>(
         &self,
         dma1: &DMA1,
-        buffer: Ref<Buffer<B, Dma1Channel4>>,
+        buffer: &Static<Buffer<B, Dma1Channel4>>,
     ) -> ::core::result::Result<(), dma::Error>
     where
         B: Unsize<[u8]>,
     {
         let usart1 = self.0;
 
-        if dma1.ccr4.read().en().is_set() {
+        if dma1.ccr4.read().en().bit_is_set() {
             return Err(dma::Error::InUse);
         }
 
         let buffer: &[u8] = buffer.lock();
 
-        dma1.cndtr4.write(|w| unsafe {
-            w.ndt().bits(u16(buffer.len()).unwrap())
-        });
-        dma1.cpar4.write(|w| unsafe {
-            w.bits(&usart1.dr as *const _ as u32)
-        });
-        dma1.cmar4.write(
-            |w| unsafe { w.bits(buffer.as_ptr() as u32) },
-        );
-        dma1.ccr4.modify(|_, w| w.en().set());
+        dma1.cndtr4
+            .write(|w| unsafe { w.ndt().bits(u16(buffer.len()).unwrap()) });
+        dma1.cpar4
+            .write(|w| unsafe { w.bits(&usart1.dr as *const _ as u32) });
+        dma1.cmar4
+            .write(|w| unsafe { w.bits(buffer.as_ptr() as u32) });
+        dma1.ccr4.modify(|_, w| w.en().set_bit());
 
         Ok(())
     }
diff --git a/src/spi.rs b/src/spi.rs
index aca530cec3d28f8f727fe767455da1971a3e53bf..d0ecfc923ca7e4a991a110114fe1c5316a64f36b 100644
--- a/src/spi.rs
+++ b/src/spi.rs
@@ -74,7 +74,7 @@ where
             });
 
             // do not remap the SPI1 pins
-            afio.mapr.modify(|_, w| w.spi1_remap().clear());
+            afio.mapr.modify(|_, w| w.spi1_remap().clear_bit());
 
             // NSS = PA4 = Alternate function push pull
             // SCK = PA5 = Alternate function push pull
@@ -130,7 +130,7 @@ where
         }
 
         // enable SS output
-        spi.cr2.write(|w| w.ssoe().set());
+        spi.cr2.write(|w| w.ssoe().set_bit());
 
         // cpha: second clock transition is the first data capture
         // cpol: CK to 1 when idle
@@ -142,23 +142,23 @@ where
         // bidimode: 2-line unidirectional
         spi.cr1.write(|w| unsafe {
             w.cpha()
-                .set()
+                .set_bit()
                 .cpol()
-                .set()
+                .set_bit()
                 .mstr()
-                .set()
+                .set_bit()
                 .br()
                 .bits(0b10)
                 .lsbfirst()
-                .clear()
+                .clear_bit()
                 .ssm()
-                .clear()
+                .clear_bit()
                 .rxonly()
-                .clear()
+                .clear_bit()
                 .dff()
-                .clear()
+                .clear_bit()
                 .bidimode()
-                .clear()
+                .clear_bit()
         });
     }
 
@@ -166,14 +166,14 @@ where
     ///
     /// **NOTE** This drives the NSS pin high
     pub fn disable(&self) {
-        self.0.cr1.modify(|_, w| w.spe().clear())
+        self.0.cr1.modify(|_, w| w.spe().clear_bit())
     }
 
     /// Enables the SPI bus
     ///
     /// **NOTE** This drives the NSS pin low
     pub fn enable(&self) {
-        self.0.cr1.modify(|_, w| w.spe().set())
+        self.0.cr1.modify(|_, w| w.spe().set_bit())
     }
 }
 
@@ -187,13 +187,13 @@ where
         let spi1 = self.0;
         let sr = spi1.sr.read();
 
-        if sr.ovr().is_set() {
+        if sr.ovr().bit_is_set() {
             Err(nb::Error::Other(Error::Overrun))
-        } else if sr.modf().is_set() {
+        } else if sr.modf().bit_is_set() {
             Err(nb::Error::Other(Error::ModeFault))
-        } else if sr.crcerr().is_set() {
+        } else if sr.crcerr().bit_is_set() {
             Err(nb::Error::Other(Error::Crc))
-        } else if sr.rxne().is_set() {
+        } else if sr.rxne().bit_is_set() {
             Ok(unsafe {
                 ptr::read_volatile(&spi1.dr as *const _ as *const u8)
             })
@@ -206,13 +206,13 @@ where
         let spi1 = self.0;
         let sr = spi1.sr.read();
 
-        if sr.ovr().is_set() {
+        if sr.ovr().bit_is_set() {
             Err(nb::Error::Other(Error::Overrun))
-        } else if sr.modf().is_set() {
+        } else if sr.modf().bit_is_set() {
             Err(nb::Error::Other(Error::ModeFault))
-        } else if sr.crcerr().is_set() {
+        } else if sr.crcerr().bit_is_set() {
             Err(nb::Error::Other(Error::Crc))
-        } else if sr.txe().is_set() {
+        } else if sr.txe().bit_is_set() {
             // NOTE(write_volatile) see note above
             unsafe {
                 ptr::write_volatile(&spi1.dr as *const _ as *mut u8, byte)
diff --git a/src/timer.rs b/src/timer.rs
index 151d4b74f073030215e2e12a00d0056a691511b2..f1acdddea5910683c1d860aae97223eaf2c0fb0c 100644
--- a/src/timer.rs
+++ b/src/timer.rs
@@ -76,7 +76,7 @@ impl<'a> Timer<'a, TIM1> {
         tim1.cr1.write(|w| w.opm().continuous());
 
         // Enable update event interrupt
-        tim1.dier.modify(|_, w| w.uie().set());
+        tim1.dier.modify(|_, w| w.uie().set_bit());
     }
 
     fn _set_timeout(&self, timeout: ::apb2::Ticks) {
@@ -120,10 +120,10 @@ impl<'a> hal::Timer for Timer<'a, TIM1> {
     }
 
     fn wait(&self) -> nb::Result<(), !> {
-        if self.0.sr.read().uif().is_clear() {
+        if self.0.sr.read().uif().bit_is_clear() {
             Err(Error::WouldBlock)
         } else {
-            self.0.sr.modify(|_, w| w.uif().clear());
+            self.0.sr.modify(|_, w| w.uif().clear_bit());
             Ok(())
         }
     }
@@ -162,7 +162,7 @@ where
         tim2.cr1.write(|w| w.opm().continuous());
 
         // Enable the update event interrupt
-        tim2.dier.modify(|_, w| w.uie().set());
+        tim2.dier.modify(|_, w| w.uie().set_bit());
     }
 
     fn _set_timeout(&self, timeout: ::apb1::Ticks) {
@@ -209,10 +209,10 @@ where
     }
 
     fn wait(&self) -> nb::Result<(), !> {
-        if self.0.sr.read().uif().is_clear() {
+        if self.0.sr.read().uif().bit_is_clear() {
             Err(Error::WouldBlock)
         } else {
-            self.0.sr.modify(|_, w| w.uif().clear());
+            self.0.sr.modify(|_, w| w.uif().clear_bit());
             Ok(())
         }
     }