diff --git a/Cargo.toml b/Cargo.toml
index 029b5e29f0190a0087ac6000f236967954724316..e1504415b039d1995b43af67660cd0fe384af1a1 100644
--- a/Cargo.toml
+++ b/Cargo.toml
@@ -13,6 +13,8 @@ cortex-m-rtic = "0.5.5"
 # embedded-hal = { version = "0.2.4", features = ["unproven"] }
 embedded-hal = "0.2.4"
 usb-device = "0.2.7"
+serde = { version = "1.0", default-features = false }
+ssmarshal = { version = "1.0", default-features = false}
 
 # Panic handlers, comment all but one to generate doc!
 panic-halt = "0.2.0"
@@ -68,17 +70,7 @@ codegen-units = 1 # better optimizations
 debug = true      # symbols are nice and they don't increase the size on Flash
 lto = true        # better optimizations
 
-<<<<<<< HEAD
-=======
-
-
 # [features]
 # nightly = ["cortex-m/inline-asm"]
 
-# # this lets you use `cargo fix`!
-# [[bin]]
-# name = "app"
-# test = false
-# bench = false
 
->>>>>>> 5e5504062ee4477abe60461125dac9cfae10ea99
diff --git a/examples/buttons.rs b/examples/buttons.rs
index 7fe324fbac4ecb95629091259c7821aa20b4ad67..38628859cf3313cac3171cd50b7bd2a706dc5964 100644
--- a/examples/buttons.rs
+++ b/examples/buttons.rs
@@ -14,7 +14,7 @@
 use core::convert::TryInto;
 
 use panic_rtt_target as _;
-use rtic::cyccnt::{Instant, U32Ext as _};
+use rtic::cyccnt::{Instant, Duration, U32Ext as _};
 use rtt_target::{rprint, rprintln, rtt_init_print};
 use stm32f4xx_hal::{gpio::{AlternateOD, PullUp}, stm32};
 
@@ -95,18 +95,20 @@ const APP: () = {
         device.GPIOA.moder.modify(|_, w| w.moder2().bits(1));
         device.GPIOA.moder.modify(|_, w| w.moder1().bits(1));
 
-        device.GPIOC.moder.modify(|_, w| w.moder5().bits(1));
+        //device.GPIOC.moder.modify(|_, w| w.moder5().bits(1));
         //left_button_read = device.GPIOCEN_R;
         let gpioa = device.GPIOA.split();
         let gpiob = device.GPIOB.split();
         let gpioc = device.GPIOC.split();        
         
+
         // pass on late resources
         init::LateResources {
             //GPIOA: device.GPIOA,
             led_red: gpioa.pa3.into_push_pull_output(),
             led_green: gpioa.pa2.into_push_pull_output(),
             led_blue: gpioa.pa1.into_push_pull_output(),
+
             turbo_button: gpioa.pa4.into_pull_down_input(),
             left_button: gpioc.pc5.into_pull_down_input(),
             right_button: gpioa.pa5.into_pull_down_input(),
@@ -118,6 +120,8 @@ const APP: () = {
             forward_button: gpiob.pb14.into_pull_down_input(),
             backward_button: gpiob.pb15.into_pull_down_input(),
         }
+
+        
     }
 
     #[idle]
@@ -131,18 +135,23 @@ const APP: () = {
     #[task(resources = [left_button, right_button, scroll_button, turbo_button, forward_button, backward_button, 
         scroll_forward, scroll_back, led_red], schedule = [is_button_pressed])]
     fn is_button_pressed(cx: is_button_pressed::Context) {
+        let mut is_pressed: bool = false;
+        let mut counter: i32 = 0;
 
         //[left,right,mouse,turbo,forward,backward]
         let mut buttons: [bool;8] = [false,false,false,false,false,false,false,false];
 
         let mut buttons_prev : [bool;8] = [false,false,false,false,false,false,false, false];
         loop {
+    
         //cx.resources.left_button.set_high().ok();
-        if cx.resources.left_button.is_high().unwrap() {
+        if cx.resources.left_button.is_high().unwrap(){
             buttons[0] = false;
             //rprintln!("left button is set high");
         } else {
             buttons[0] = true;
+            //is_pressed = true;
+            //let start = Instant::now();
             //rprintln!("left button is set low");
         }
 
@@ -199,77 +208,26 @@ const APP: () = {
         }
 
         if buttons != buttons_prev{
-
-            rprintln!("Buttons -- Right: {}, Left: {}, Middle: {}, DPI: {}, Fram: {}, Bak: {}, scroll forward: {}, scroll back: {}", buttons[0], buttons[1], buttons[2], buttons[3], 
+            buttons_prev = buttons;
+            rprintln!("Buttons -- Left: {}, Right: {}, Middle: {}, DPI: {}, Fram: {}, Bak: {}, scroll forward: {}, scroll back: {}", buttons[0], buttons[1], buttons[2], buttons[3], 
                 buttons[4],buttons[5], buttons[6], buttons[7]);
 
-            //rprintln!(print);
-            buttons_prev = buttons;
+            loop {
+                counter = counter + 1;
+                if counter > 1000 {
+                    counter = 0;
+                    break;
+                }
+            }
+            
         }
 
 
+
     }
     }
 
 
-    #[task(resources = [led_green,led_blue,led_red], schedule = [toggle])]
-    fn toggle(cx: toggle::Context, mut no_toggled: i32) {
-        static mut TOGGLE: bool = false;
-        //rprintln!("toggle  @ {:?}", Instant::now());
-        //rprintln!("times I have toggled {:?}", no_toggled);
-        no_toggled +=1;
-
-        /*if no_toggled % 8 == 0{
-            rprintln!("White");
-            cx.resources.led_red.set_high().ok();
-            cx.resources.led_green.set_high().ok();
-            cx.resources.led_blue.set_high().ok();
-        } else if no_toggled % 8 == 1{
-            rprintln!("Green-yellow"); //Needs more oomph to be real yellow.
-            cx.resources.led_red.set_high().ok();
-            cx.resources.led_blue.set_low().ok();
-            cx.resources.led_green.set_high().ok();
-        } else if no_toggled % 8 == 2{
-            rprintln!("Purple");
-            cx.resources.led_red.set_high().ok();
-            cx.resources.led_blue.set_high().ok();
-            cx.resources.led_green.set_low().ok();
-        } else if no_toggled % 8 == 3{
-            rprintln!("Light blue");
-            cx.resources.led_red.set_low().ok();
-            cx.resources.led_blue.set_high().ok();
-            cx.resources.led_green.set_high().ok();
-        } else if no_toggled % 8 == 4{
-            rprintln!("Red");
-            cx.resources.led_red.set_high().ok();
-            cx.resources.led_blue.set_low().ok();
-            cx.resources.led_green.set_low().ok();
-        } else if no_toggled % 8 == 5{
-            rprintln!("Green");
-            cx.resources.led_red.set_low().ok();
-            cx.resources.led_blue.set_low().ok();
-            cx.resources.led_green.set_high().ok();
-        } else if no_toggled % 8 == 6{
-            rprintln!("Blue");
-            cx.resources.led_red.set_low().ok();
-            cx.resources.led_blue.set_high().ok();
-            cx.resources.led_green.set_low().ok();
-        } else {
-            rprintln!("Off");
-            cx.resources.led_red.set_low().ok();
-            cx.resources.led_blue.set_low().ok();
-            cx.resources.led_green.set_low().ok();
-        }*/
-        rprintln!("printing");
-        rprintln!("White");
-        cx.resources.led_red.set_high().ok();
-        cx.resources.led_green.set_high().ok();
-        cx.resources.led_blue.set_high().ok();
-
-        //*TOGGLE = !*TOGGLE;
-        //cx.schedule.toggle(cx.scheduled + OFFSET.cycles(),no_toggled).unwrap();
-    }
-
     extern "C" {
         fn EXTI0();
         fn USART1();
diff --git a/examples/main.rs b/examples/main.rs
new file mode 100644
index 0000000000000000000000000000000000000000..0e4b3233c228849327641a254204a74f30a5dfe2
--- /dev/null
+++ b/examples/main.rs
@@ -0,0 +1,304 @@
+//Work made by J, Jacobsson, T. Andersson and S. Gradén.
+//Tested and valideted on:
+//Windows - Lenovo Yoga 7 series
+//Mac - Apple MacBook Pro Model A2141 EMC 3347
+//TODO:
+//Forward and back buttons should work as normal buttons.
+//RGB should be able to be configured in the computer.
+
+#![no_main]
+#![no_std]
+
+use stm32f4xx_hal::{
+    //dwt::Dwt,
+    gpio::Speed,
+    gpio::{gpioa::{PA1, PA2, PA3, PA4, PA5, PA6, PA7},
+        gpiob::{PB10, PB12, PB14,PB15},
+        gpioc::{PC2, PC3, PC4, PC5},
+        Alternate, Output, PushPull, Input, PullDown,// PullUp, 
+    },
+    //rcc::Clocks,
+    spi::Spi,
+    //stm32,
+    otg_fs::{UsbBus, UsbBusType, USB}, //USB
+    prelude::*,
+};
+use usb_device::{bus::UsbBusAllocator, prelude::*};
+use usbd_hid::{
+    descriptor::{generator_prelude::*, MouseReport},
+    hid_class::HIDClass,
+};
+
+use embedded_hal::spi::MODE_3;
+use rtic::cyccnt::{Instant, U32Ext as _};
+use panic_rtt_target as _;
+use rtt_target::{rprintln, rtt_init_print};
+
+use app::{
+    pmw3389::{self, Register},
+    DwtDelay,
+};
+
+//Some settings for the sensor.
+type PMW3389T = pmw3389::Pmw3389<
+    Spi<
+        stm32f4xx_hal::stm32::SPI2,
+        (
+            PB10<Alternate<stm32f4xx_hal::gpio::AF5>>,
+            PC2<Alternate<stm32f4xx_hal::gpio::AF5>>,
+            PC3<Alternate<stm32f4xx_hal::gpio::AF5>>,
+        ),
+    >,
+    PB12<Output<PushPull>>,
+>;
+
+#[rtic::app(device = stm32f4xx_hal::stm32, peripherals = true)]
+const APP: () = {
+    struct Resources {
+        // late resources
+        // Leds
+        // led_blue: PA1<Output<PushPull>>,
+        // led_red: PA3<Output<PushPull>>,
+        // led_green: PA2<Output<PushPull>>,
+
+        // Buttons
+        // turbo_button: PA4<Input<PullDown>>,
+        right_button: PA5<Input<PullDown>>,
+        scroll_button: PA6<Input<PullDown>>,
+        forward_button: PB14<Input<PullDown>>,
+        // backward_button: PB15<Input<PullDown>>,
+        left_button: PC5<Input<PullDown>>,
+
+        // Scroll
+        scroll_b: PC4<Input<PullDown>>,
+        scroll_a: PA7<Input<PullDown>>,
+
+        // USB
+        hid: HIDClass<'static, UsbBusType>,
+        usb_dev: UsbDevice<'static, UsbBus<USB>>,
+        
+        //Sensor
+        pmw3389: PMW3389T, 
+    }
+
+    #[init]
+    fn init(mut ctx: init::Context) -> init::LateResources {
+        static mut EP_MEMORY: [u32; 1024] = [0; 1024];
+        static mut USB_BUS: Option<UsbBusAllocator<UsbBusType>> = None;
+
+        rtt_init_print!();
+        rprintln!("init");
+
+        // Set up the system clock.
+        let rcc = ctx.device.RCC.constrain();
+        let _clocks = rcc.cfgr.sysclk(48.mhz()).require_pll48clk().freeze();
+
+        // Initialize (enable) the monotonic timer (CYCCNT)
+        ctx.core.DCB.enable_trace();
+        ctx.core.DWT.enable_cycle_counter();
+        
+        // Buttons
+        // ||||||||||
+        // \/\/\/\/\/
+        
+        let gpioa = ctx.device.GPIOA.split();
+        let gpiob = ctx.device.GPIOB.split();
+        let gpioc = ctx.device.GPIOC.split();
+        let left_button = gpioc.pc5.into_pull_down_input();
+        let right_button = gpioa.pa5.into_pull_down_input();
+        let scroll_button = gpioa.pa6.into_pull_down_input();
+        let forward_button = gpiob.pb14.into_pull_down_input();
+        // /\/\/\/\/\
+        // ||||||||||
+        // Buttons
+
+        //Scroll
+        let scroll_a = gpioa.pa7.into_pull_down_input();
+        let scroll_b = gpioc.pc4.into_pull_down_input();
+
+        // Sensor Init
+        // ||||||||||
+        // \/\/\/\/\/
+        let mut core = ctx.core;
+
+        // Initialize (enable) the monotonic timer (CYCCNT)
+        core.DCB.enable_trace();
+        core.DWT.enable_cycle_counter();
+
+        // setup clocks Duplicate code
+        //let rcc = ctx.device.RCC.constrain();
+        //let clocks = rcc.cfgr.freeze();
+        rprintln!("clocks:");
+        rprintln!("hclk {}", _clocks.hclk().0);
+
+        // Configure SPI
+        let sck = gpiob.pb10.into_alternate_af5();
+        let miso = gpioc.pc2.into_alternate_af5();
+        let mosi = gpioc.pc3.into_alternate_af5();
+        let cs = gpiob.pb12.into_push_pull_output().set_speed(Speed::High);
+
+        let spi = Spi::spi2(
+            ctx.device.SPI2,
+            (sck, miso, mosi),
+            MODE_3,
+            stm32f4xx_hal::time::KiloHertz(2000).into(),
+            _clocks,
+        );
+
+        let delay = DwtDelay::new(&mut core.DWT, _clocks);
+        let mut pmw3389 = pmw3389::Pmw3389::new(spi, cs, delay).unwrap();
+
+        // set in burst mode
+        pmw3389.write_register(Register::MotionBurst, 0x00);
+        // /\/\/\/\/\
+        // ||||||||||
+        // Sensor Init
+
+        // USB
+        // ||||||||||
+        // \/\/\/\/\/
+        let usb = USB {
+            usb_global: ctx.device.OTG_FS_GLOBAL,
+            usb_device: ctx.device.OTG_FS_DEVICE,
+            usb_pwrclk: ctx.device.OTG_FS_PWRCLK,
+            pin_dm: gpioa.pa11.into_alternate_af10(),
+            pin_dp: gpioa.pa12.into_alternate_af10(),
+        };
+        USB_BUS.replace(UsbBus::new(usb, EP_MEMORY));
+        
+        let hid = HIDClass::new(USB_BUS.as_ref().unwrap(), MouseReport::desc(), 1);
+        let usb_dev = UsbDeviceBuilder::new(USB_BUS.as_ref().unwrap(), UsbVidPid(0xc410, 0x0000))
+            .manufacturer("Nuttali")
+            .product("Mouse")
+            .serial_number("1.0")
+            .device_class(0)
+            .build();
+        
+        // /\/\/\/\/\
+        // ||||||||||
+        // USB
+        
+        init::LateResources{ left_button,right_button,scroll_button,forward_button, hid, usb_dev, pmw3389, scroll_b, scroll_a}
+    }
+
+    #[task(binds=OTG_FS, resources = [left_button, right_button,scroll_button,forward_button, hid, usb_dev, pmw3389, scroll_a, scroll_b])]
+    fn on_usb(ctx: on_usb::Context) {
+        static mut WHEEL_COUNT: i8 = 0;
+        static mut A_PREV :bool = false;
+        static mut B_PREV :bool = false;
+        
+        // destruct the context
+        let (left_button, right_button, scroll_button, forward_button,
+            usb_dev, hid, pmw3389, scroll_a, scroll_b) 
+            = (ctx.resources.left_button, ctx.resources.right_button,
+               ctx.resources.scroll_button,
+               ctx.resources.forward_button, ctx.resources.usb_dev, 
+               ctx.resources.hid, ctx.resources.pmw3389, ctx.resources.scroll_a,
+               ctx.resources.scroll_b);
+
+        let a:bool = scroll_a.is_high().unwrap();
+        let b:bool = scroll_b.is_high().unwrap();
+        *WHEEL_COUNT = check_scroll(a,b,*A_PREV,*B_PREV);
+        *A_PREV = a;
+        *B_PREV = b;
+        
+        // Read from sensor
+        let (x_sensor, y_sensor) = pmw3389.read_status().unwrap();
+        
+        let left:u8;
+        if left_button.is_low().unwrap(){
+            left = 1;
+        }else{
+            left = 0;
+        }
+        let right:u8;
+        if right_button.is_low().unwrap(){
+            right = 2;
+        }else{
+            right = 0;
+        }
+        let scroll:u8;
+        if scroll_button.is_high().unwrap(){
+            //rprintln!("scroll"); 
+            scroll = 4;
+        }else{
+            scroll = 0;
+        }
+
+        //This dose not work yet.
+        let forward:u8;
+        if forward_button.is_high().unwrap(){
+            //rprintln!("forward"); 
+            forward = 8;
+        }else{
+            forward = 0;
+        }
+
+
+        
+
+        //https://eleccelerator.com/tutorial-about-usb-hid-report-descriptors/
+        let report = MouseReport {
+            x: (x_sensor as i8)>> 1, // need to convert form i16 to i8. Shifts to get smother movement
+            y: (y_sensor as i8)>> 1, // need to convert form i16 to i8. Shifts to get smother movement
+            buttons: left+right+scroll+forward, // (into takes a bool into an integer)
+            wheel: *WHEEL_COUNT,
+        };
+
+        // push the report
+        hid.push_input(&report).ok();
+
+        // update the usb device state
+        if usb_dev.poll(&mut [hid]) {
+            return;
+        }
+    }
+
+    #[idle]
+    fn idle(_cx: idle::Context) -> ! {
+        rprintln!("idle");
+        loop {
+            continue;
+        }
+    }
+};
+
+fn check_scroll(scroll_a:bool, scroll_b:bool, scroll_a_prev:bool, scroll_b_prev:bool) -> i8{
+    let mut wheel_count: i8 = 0;
+
+    if scroll_a != scroll_a_prev || scroll_b != scroll_b_prev{
+
+        //Sequence for up:
+        //A:Low  B:Low
+        //A:High B:Low
+        //B:High B:High
+        //A:Low  B:High
+        //A:Low  B:Low
+
+        //Sequence for down:
+        //A:Low  B:Low
+        //A:Low  B:High
+        //A:High B:High
+        //A:High B:Low
+        //A:Low  B:Low
+
+        if scroll_a_prev==scroll_b_prev{
+            if scroll_b==scroll_b_prev{
+                wheel_count +=1;
+                //rprintln!("Up count:{}", WHEEL_COUNT)
+            }else{
+                wheel_count -=1;
+                //rprintln!("Down count:{}", WHEEL_COUNT)
+            }
+        }else{
+            if scroll_a==scroll_a_prev{
+                wheel_count +=1;
+                //rprintln!("Up count:{}", WHEEL_COUNT)
+            }else{
+                wheel_count -=1;
+                //rprintln!("Down count:{}", WHEEL_COUNT)
+            }
+        }
+    }
+    return wheel_count;
+}
diff --git a/examples/nuttali_scroll.rs b/examples/nuttali_scroll.rs
new file mode 100644
index 0000000000000000000000000000000000000000..887db65f347a671adb29218cd0c59e5c085dc515
--- /dev/null
+++ b/examples/nuttali_scroll.rs
@@ -0,0 +1,257 @@
+//! nuttali_scroll
+//!
+//! HAL OutputPin abstractions
+//!
+//! What it covers:
+//! - using embedded hal, and the OutputPin abstraction
+
+#![no_main]
+#![no_std]
+
+
+//use core::intrinsics::rotate_left;
+
+use core::convert::TryInto;
+
+use panic_rtt_target as _;
+use rtic::cyccnt::{Instant, U32Ext as _};
+use rtt_target::{rprint, rprintln, rtt_init_print};
+use stm32f4xx_hal::{gpio::{AlternateOD, PullUp}, stm32};
+
+use stm32f4xx_hal::{
+    gpio::{
+        gpioa::{
+            PA1, PA2, PA3, PA4, PA5, PA6, PA7},
+        gpiob::{
+            PB14,PB15},
+        gpioc::{
+            PC4, PC5}, 
+    Input, Output, PushPull, PullDown, Alternate},
+    prelude::*,
+};
+
+use embedded_hal::digital::v2::{OutputPin, ToggleableOutputPin, InputPin};
+
+const OFFSET: u32 = 50_000_000;
+
+#[rtic::app(device = stm32f4xx_hal::stm32, monotonic = rtic::cyccnt::CYCCNT, peripherals = true)]
+const APP: () = {
+    struct Resources {
+        // late resources
+        //GPIOA: stm32::GPIOA,
+        led_blue: PA1<Output<PushPull>>,
+        led_red: PA3<Output<PushPull>>,
+        led_green: PA2<Output<PushPull>>,
+    
+        turbo_button: PA4<Input<PullDown>>,
+        right_button: PA5<Input<PullDown>>,
+        scroll_button: PA6<Input<PullDown>>,
+
+        scroll_B: PC4<Input<PullDown>>,
+        scroll_A: PA7<Input<PullDown>>,
+
+        forward_button: PB14<Input<PullDown>>,
+        backward_button: PB15<Input<PullDown>>,
+
+        left_button: PC5<Input<PullDown>>,
+
+
+    }
+    //#[init(schedule = [toggle])]
+    #[init(schedule = [is_button_pressed])]
+    fn init(cx: init::Context) -> init::LateResources {
+        rtt_init_print!();
+        rprintln!("init");
+
+
+        let mut core = cx.core;
+        let device = cx.device;
+
+
+        // Initialize (enable) the monotonic timer (CYCCNT)
+        core.DCB.enable_trace();
+        core.DWT.enable_cycle_counter();
+
+        // semantically, the monotonic timer is frozen at time "zero" during `init`
+        // NOTE do *not* call `Instant::now` in this context; it will return a nonsense value
+        let now = cx.start; // the start time of the system
+
+        // Schedule `toggle` to run 8e6 cycles (clock cycles) in the future
+        //let number_of_toggles = 0;
+        //cx.schedule.toggle(now + OFFSET.cycles(),number_of_toggles).unwrap();
+
+        cx.schedule.is_button_pressed(now + OFFSET.cycles()).unwrap();
+
+        
+        //let left_button = gpioc.pc5.into_pull_up_input();
+        //let left_button_timer = dp.TIM2;
+
+        // power on GPIOA, RM0368 6.3.11
+        //device.RCC.ahb1enr.modify(|_, w| w.gpioaen().set_bit());
+        
+        //device.RCC.ahb1enr.modify(|_, w| w.gpiocen().set_bit());
+        //configure PA3 as output, RM0368 8.4.1
+        device.GPIOA.moder.modify(|_, w| w.moder3().bits(1));
+        device.GPIOA.moder.modify(|_, w| w.moder2().bits(1));
+        device.GPIOA.moder.modify(|_, w| w.moder1().bits(1));
+
+        device.GPIOC.moder.modify(|_, w| w.moder5().bits(1));
+        //left_button_read = device.GPIOCEN_R;
+        let gpioa = device.GPIOA.split();
+        let gpiob = device.GPIOB.split();
+        let gpioc = device.GPIOC.split();        
+        
+        // pass on late resources
+        init::LateResources {
+            //GPIOA: device.GPIOA,
+            led_red: gpioa.pa3.into_push_pull_output(),
+            led_green: gpioa.pa2.into_push_pull_output(),
+            led_blue: gpioa.pa1.into_push_pull_output(),
+            turbo_button: gpioa.pa4.into_pull_down_input(),
+            left_button: gpioc.pc5.into_pull_down_input(),
+            right_button: gpioa.pa5.into_pull_down_input(),
+
+            scroll_B: gpioc.pc4.into_pull_down_input(),
+            scroll_button: gpioa.pa6.into_pull_down_input(),
+            scroll_A: gpioa.pa7.into_pull_down_input(),
+
+            forward_button: gpiob.pb14.into_pull_down_input(),
+            backward_button: gpiob.pb15.into_pull_down_input(),
+        }
+    }
+
+    #[idle]
+    fn idle(_cx: idle::Context) -> ! {
+        rprintln!("idle");
+        loop {
+            continue;
+        }
+    }
+
+    #[task(resources = [scroll_A, scroll_B], schedule = [is_button_pressed])]
+    fn is_button_pressed(cx: is_button_pressed::Context) {
+        //[left,right,mouse,turbo,forward,backward]
+        let mut counter: i32 = 0;
+        let mut scroll: [bool;2] = [false,false];
+
+        let mut scroll_prev : [bool;2] = [false,false];
+        loop {
+            
+            if cx.resources.scroll_A.is_high().unwrap(){
+                scroll[0] = true
+            } else {
+                scroll[0] = false;
+            }
+
+            if cx.resources.scroll_B.is_high().unwrap(){
+                scroll[1] = true
+            } else {
+                scroll[1] = false;
+            }
+
+            if scroll != scroll_prev{
+
+                //Sequence for up:
+                //A:Low  B:Low
+                //A:High B:Low
+                //B:High B:High
+                //A:Low  B:High
+                //A:Low  B:Low
+
+                //Sequence for down:
+                //A:Low  B:Low
+                //A:Low  B:High
+                //A:High B:High
+                //A:High B:Low
+                //A:Low  B:Low
+
+                if scroll_prev[0]==scroll_prev[1]{
+                    if scroll[1]==scroll_prev[1]{
+                        counter +=1;
+                        rprintln!("Up count:{}",counter)
+                    }else{
+                        counter -=1;
+                        rprintln!("Down count:{}",counter)
+                    }
+                }else{
+                    if scroll[0]==scroll_prev[0]{
+                        counter +=1;
+                        rprintln!("Up count:{}",counter)
+                    }else{
+                        counter -=1;
+                        rprintln!("Down count:{}",counter)
+                    }
+                }
+
+                //rprintln!(print);
+                scroll_prev = scroll;
+            }
+
+
+        }
+    }
+
+
+    #[task(resources = [led_green,led_blue,led_red], schedule = [toggle])]
+    fn toggle(cx: toggle::Context, mut no_toggled: i32) {
+        static mut TOGGLE: bool = false;
+        //rprintln!("toggle  @ {:?}", Instant::now());
+        //rprintln!("times I have toggled {:?}", no_toggled);
+        no_toggled +=1;
+
+        /*if no_toggled % 8 == 0{
+            rprintln!("White");
+            cx.resources.led_red.set_high().ok();
+            cx.resources.led_green.set_high().ok();
+            cx.resources.led_blue.set_high().ok();
+        } else if no_toggled % 8 == 1{
+            rprintln!("Green-yellow"); //Needs more oomph to be real yellow.
+            cx.resources.led_red.set_high().ok();
+            cx.resources.led_blue.set_low().ok();
+            cx.resources.led_green.set_high().ok();
+        } else if no_toggled % 8 == 2{
+            rprintln!("Purple");
+            cx.resources.led_red.set_high().ok();
+            cx.resources.led_blue.set_high().ok();
+            cx.resources.led_green.set_low().ok();
+        } else if no_toggled % 8 == 3{
+            rprintln!("Light blue");
+            cx.resources.led_red.set_low().ok();
+            cx.resources.led_blue.set_high().ok();
+            cx.resources.led_green.set_high().ok();
+        } else if no_toggled % 8 == 4{
+            rprintln!("Red");
+            cx.resources.led_red.set_high().ok();
+            cx.resources.led_blue.set_low().ok();
+            cx.resources.led_green.set_low().ok();
+        } else if no_toggled % 8 == 5{
+            rprintln!("Green");
+            cx.resources.led_red.set_low().ok();
+            cx.resources.led_blue.set_low().ok();
+            cx.resources.led_green.set_high().ok();
+        } else if no_toggled % 8 == 6{
+            rprintln!("Blue");
+            cx.resources.led_red.set_low().ok();
+            cx.resources.led_blue.set_high().ok();
+            cx.resources.led_green.set_low().ok();
+        } else {
+            rprintln!("Off");
+            cx.resources.led_red.set_low().ok();
+            cx.resources.led_blue.set_low().ok();
+            cx.resources.led_green.set_low().ok();
+        }*/
+        rprintln!("printing");
+        rprintln!("White");
+        cx.resources.led_red.set_high().ok();
+        cx.resources.led_green.set_high().ok();
+        cx.resources.led_blue.set_high().ok();
+
+        //*TOGGLE = !*TOGGLE;
+        //cx.schedule.toggle(cx.scheduled + OFFSET.cycles(),no_toggled).unwrap();
+    }
+
+    extern "C" {
+        fn EXTI0();
+        fn USART1();
+    }
+};
diff --git a/examples/pmw3389.rs b/examples/pmw3389.rs
index 0d3cc8edf424f1806c21d2a97ea8a51e128ff5ee..cd4d763a09697b4e59710c6a284313cb52dc120c 100644
--- a/examples/pmw3389.rs
+++ b/examples/pmw3389.rs
@@ -11,11 +11,7 @@ use stm32f4xx_hal::{
     dwt::Dwt,
     gpio::Speed,
     gpio::{
-<<<<<<< HEAD
         gpiob::{PB10, PB12},
-=======
-        gpiob::{PB10, PB4},
->>>>>>> 5e5504062ee4477abe60461125dac9cfae10ea99
         gpioc::{PC2, PC3},
         Alternate, Output, PushPull,
     },
@@ -40,11 +36,7 @@ type PMW3389T = pmw3389::Pmw3389<
             PC3<Alternate<stm32f4xx_hal::gpio::AF5>>,
         ),
     >,
-<<<<<<< HEAD
     PB12<Output<PushPull>>,
-=======
-    PB4<Output<PushPull>>,
->>>>>>> 5e5504062ee4477abe60461125dac9cfae10ea99
 >;
 
 #[rtic::app(device = stm32f4xx_hal::stm32, monotonic = rtic::cyccnt::CYCCNT, peripherals = true)]
@@ -76,7 +68,7 @@ const APP: () = {
         // sck    - pb10, (yellow)
         // miso   - pc2, (red)
         // mosi   - pc3, (orange)
-        // ncs    - pb4, (long yellow)
+        // ncs    - pb12, (long yellow)
         // motion - (brown)
         //
         // +5, (white)
@@ -88,11 +80,7 @@ const APP: () = {
         let sck = gpiob.pb10.into_alternate_af5();
         let miso = gpioc.pc2.into_alternate_af5();
         let mosi = gpioc.pc3.into_alternate_af5();
-<<<<<<< HEAD
         let cs = gpiob.pb12.into_push_pull_output().set_speed(Speed::High);
-=======
-        let cs = gpiob.pb4.into_push_pull_output().set_speed(Speed::High);
->>>>>>> 5e5504062ee4477abe60461125dac9cfae10ea99
 
         let spi = Spi::spi2(
             device.SPI2,
@@ -122,15 +110,17 @@ const APP: () = {
     fn poll(cx: poll::Context) {
         static mut COUNTER: u32 = 0;
         static mut POS_X: i64 = 0;
+        static mut POS_Y: i64 = 0;
 
         *COUNTER += 1;
         if *COUNTER == 1000 / RATIO {
-            cx.spawn.trace(*POS_X).unwrap();
+            cx.spawn.trace(*POS_X,*POS_Y).unwrap();
             *COUNTER = 0;
         }
 
-        let (x, _y) = cx.resources.pmw3389.read_status().unwrap();
+        let (x, y) = cx.resources.pmw3389.read_status().unwrap();
         *POS_X += x as i64;
+        *POS_Y += y as i64;
 
         // task should run each second N ms (16_000 cycles at 16MHz)
         cx.schedule
@@ -139,15 +129,19 @@ const APP: () = {
     }
 
     #[task(priority = 1)]
-    fn trace(_cx: trace::Context, pos: i64) {
-        static mut OLD_POS: i64 = 0;
+    fn trace(_cx: trace::Context, pos_x: i64, pos_y: i64) {
+        static mut OLD_POS_X: i64 = 0;
+        static mut OLD_POS_Y: i64 = 0;
         rprintln!(
-            "pos_x {:010}, diff {:010} @{:?}",
-            pos,
-            pos - *OLD_POS,
+            "pos_x {:010}, diff_x {:010}, pos_y {:010}, diff_y {:010} @{:?}",
+            pos_x,
+            pos_x - *OLD_POS_X,
+            pos_y,
+            pos_y - *OLD_POS_Y,
             Instant::now()
         );
-        *OLD_POS = pos;
+        *OLD_POS_X = pos_x;
+        *OLD_POS_Y = pos_y;
     }
 
     #[idle]
diff --git a/examples/rtt_rtic_usb_mouse.rs b/examples/rtt_rtic_usb_mouse.rs
index 7bb3347a607f48c70bc23c468a133d1776c0fcb2..441a2fe212cb9e2550c797407466e0cb4191e9f3 100644
--- a/examples/rtt_rtic_usb_mouse.rs
+++ b/examples/rtt_rtic_usb_mouse.rs
@@ -71,7 +71,7 @@ pub mod hid {
 
     pub fn report(x: i8, y: i8) -> [u8; 3] {
         [
-            0x00,    // button: none
+            0x09,    // button: none
             x as u8, // x-axis
             y as u8, // y-axis
         ]
@@ -257,7 +257,7 @@ const APP: () = {
         let hid = HIDClass::new(USB_BUS.as_ref().unwrap());
 
         let usb_dev = UsbDeviceBuilder::new(USB_BUS.as_ref().unwrap(), UsbVidPid(0xc410, 0x0000))
-            .manufacturer("Fake company")
+            .manufacturer("Nuttali")
             .product("mouse")
             .serial_number("TEST")
             .device_class(0)
@@ -296,10 +296,10 @@ const APP: () = {
         // move mouse cursor horizontally (x-axis) while blinking LED
         if *counter < P / 2 {
             led.set_high().ok();
-            hid.write(&hid::report(10, 0));
+            hid.write(&hid::report(10, 10));
         } else {
             led.set_low().ok();
-            hid.write(&hid::report(-10, 0));
+            hid.write(&hid::report(-10, -10));
         }
     }
 
diff --git a/examples/usb_mouse.rs b/examples/usb_mouse.rs
new file mode 100644
index 0000000000000000000000000000000000000000..355dfba8f97c41f73374806c827b8c1cd1b6dceb
--- /dev/null
+++ b/examples/usb_mouse.rs
@@ -0,0 +1,377 @@
+// > cargo run usb-mouse
+// or
+// > cargo run usb-mouse --release
+
+#![no_main]
+#![no_std]
+
+use stm32f4xx_hal::{
+    dwt::Dwt,
+    gpio::Speed,
+    gpio::{gpioa::{PA1, PA2, PA3, PA4, PA5, PA6, PA7},
+        gpiob::{PB10, PB12, PB14,PB15},
+        gpioc::{PC2, PC3, PC4, PC5},
+        Alternate, Output, PushPull, Input, PullDown,// PullUp, 
+    },
+    rcc::Clocks,
+    spi::Spi,
+    stm32,
+    otg_fs::{UsbBus, UsbBusType, USB}, //USB
+    prelude::*,
+};
+use usb_device::{bus::UsbBusAllocator, prelude::*};
+use usbd_hid::{
+    descriptor::{generator_prelude::*, MouseReport},
+    hid_class::HIDClass,
+};
+
+use embedded_hal::spi::MODE_3;
+use rtic::cyccnt::{Instant, U32Ext as _};
+use panic_rtt_target as _;
+use rtt_target::{rprintln, rtt_init_print};
+
+use app::{
+    pmw3389::{self, Register},
+    DwtDelay,
+};
+
+//Some settings for the sensor.
+type PMW3389T = pmw3389::Pmw3389<
+    Spi<
+        stm32f4xx_hal::stm32::SPI2,
+        (
+            PB10<Alternate<stm32f4xx_hal::gpio::AF5>>,
+            PC2<Alternate<stm32f4xx_hal::gpio::AF5>>,
+            PC3<Alternate<stm32f4xx_hal::gpio::AF5>>,
+        ),
+    >,
+    PB12<Output<PushPull>>,
+>;
+
+#[rtic::app(device = stm32f4xx_hal::stm32, peripherals = true)]
+const APP: () = {
+    struct Resources {
+        // late resources
+        // Leds
+        led_blue: PA1<Output<PushPull>>,
+        led_red: PA3<Output<PushPull>>,
+        led_green: PA2<Output<PushPull>>,
+
+        // Buttons
+        dpi_button: PA4<Input<PullDown>>,
+         right_button: PA5<Input<PullDown>>,
+         scroll_button: PA6<Input<PullDown>>,
+         forward_button: PB14<Input<PullDown>>,
+        backward_button: PB15<Input<PullDown>>,
+        left_button: PC5<Input<PullDown>>,
+
+        // Scroll
+        scroll_B: PC4<Input<PullDown>>,
+        scroll_A: PA7<Input<PullDown>>,
+
+        // USB
+        hid: HIDClass<'static, UsbBusType>,
+        usb_dev: UsbDevice<'static, UsbBus<USB>>,
+        
+        //Sensor
+        pmw3389: PMW3389T, 
+        
+
+    }
+
+    #[init]
+    fn init(mut ctx: init::Context) -> init::LateResources {
+        static mut EP_MEMORY: [u32; 1024] = [0; 1024];
+        static mut USB_BUS: Option<UsbBusAllocator<UsbBusType>> = None;
+        static mut dpi_button_prev: bool = false;
+
+        rtt_init_print!();
+    
+        rprintln!("init");
+
+        // Set up the system clock.
+        let rcc = ctx.device.RCC.constrain();
+        let _clocks = rcc.cfgr.sysclk(48.mhz()).require_pll48clk().freeze();
+
+        // Initialize (enable) the monotonic timer (CYCCNT)
+        ctx.core.DCB.enable_trace();
+        ctx.core.DWT.enable_cycle_counter();
+        // Leds
+       
+
+
+        // Buttons
+        // ||||||||||
+        // \/\/\/\/\/
+        
+        let gpioa = ctx.device.GPIOA.split();
+        let gpiob = ctx.device.GPIOB.split();
+        let gpioc = ctx.device.GPIOC.split();
+
+        let led_red = gpioa.pa3.into_push_pull_output();
+        let led_green = gpioa.pa2.into_push_pull_output();
+        let led_blue = gpioa.pa1.into_push_pull_output();
+
+
+        let left_button = gpioc.pc5.into_pull_down_input();
+        let right_button = gpioa.pa5.into_pull_down_input();
+        let scroll_button = gpioa.pa6.into_pull_down_input();
+
+        let dpi_button = gpioa.pa4.into_pull_down_input();
+
+        let forward_button = gpiob.pb14.into_pull_down_input();
+        let backward_button = gpiob.pb15.into_pull_down_input();
+
+        
+        // /\/\/\/\/\
+        // ||||||||||
+        // Buttons
+
+        //Scroll
+        let scroll_A = gpioa.pa7.into_pull_down_input();
+        let scroll_B = gpioc.pc4.into_pull_down_input();
+
+        // Sensor Init
+        // ||||||||||
+        // \/\/\/\/\/
+        let mut core = ctx.core;
+
+        // Initialize (enable) the monotonic timer (CYCCNT)
+        core.DCB.enable_trace();
+        core.DWT.enable_cycle_counter();
+
+        // setup clocks Duplicate code
+        //let rcc = ctx.device.RCC.constrain();
+        //let clocks = rcc.cfgr.freeze();
+        rprintln!("clocks:");
+        rprintln!("hclk {}", _clocks.hclk().0);
+
+        // Configure SPI
+        let sck = gpiob.pb10.into_alternate_af5();
+        let miso = gpioc.pc2.into_alternate_af5();
+        let mosi = gpioc.pc3.into_alternate_af5();
+        let cs = gpiob.pb12.into_push_pull_output().set_speed(Speed::High);
+
+        let spi = Spi::spi2(
+            ctx.device.SPI2,
+            (sck, miso, mosi),
+            MODE_3,
+            stm32f4xx_hal::time::KiloHertz(2000).into(),
+            _clocks,
+        );
+
+        let mut delay = DwtDelay::new(&mut core.DWT, _clocks);
+        let mut pmw3389 = pmw3389::Pmw3389::new(spi, cs, delay).unwrap();
+
+        // set in burst mode
+        pmw3389.write_register(Register::MotionBurst, 0x00);
+        // /\/\/\/\/\
+        // ||||||||||
+        // Sensor Init
+
+        // USB
+        // ||||||||||
+        // \/\/\/\/\/
+        let usb = USB {
+            usb_global: ctx.device.OTG_FS_GLOBAL,
+            usb_device: ctx.device.OTG_FS_DEVICE,
+            usb_pwrclk: ctx.device.OTG_FS_PWRCLK,
+            pin_dm: gpioa.pa11.into_alternate_af10(),
+            pin_dp: gpioa.pa12.into_alternate_af10(),
+        };
+        USB_BUS.replace(UsbBus::new(usb, EP_MEMORY));
+        
+        let hid = HIDClass::new(USB_BUS.as_ref().unwrap(), MouseReport::desc(), 1);
+        let usb_dev = UsbDeviceBuilder::new(USB_BUS.as_ref().unwrap(), UsbVidPid(0xc410, 0x0000))
+            .manufacturer("Nuttali")
+            .product("Mouse")
+            .serial_number("1.0")
+            .device_class(0)
+            .build();
+        
+        // /\/\/\/\/\
+        // ||||||||||
+        // USB
+        
+        init::LateResources{ left_button,right_button, scroll_button, hid, usb_dev, pmw3389, scroll_B, scroll_A, 
+            dpi_button, forward_button,backward_button,led_red,led_blue,led_green}
+    }
+
+    #[task(binds=OTG_FS, resources = [left_button, right_button, scroll_button, hid, usb_dev, pmw3389, scroll_A,
+         scroll_B, dpi_button,forward_button, backward_button, led_red, led_blue, led_green])]
+    fn on_usb(ctx: on_usb::Context) {
+        static mut wheel_count: i8 = 0;
+        static mut a_prev :bool = false;
+        static mut b_prev :bool = false;
+
+        static mut dpi_toggle_prev :bool = false;
+        static mut dpi_toggle: i8 = 0;
+        static mut dpi_settings: [i8; 2] = [2, 8];
+        static mut dpi_button_prev: bool = false;
+
+        static mut forward_button_pressed: bool = false;
+        static mut backward_button_pressed: bool = false;
+        static mut wrapping_led_counter:u8 = 0;
+
+        // destruct the context
+        let (left_button, right_button,scroll_button, usb_dev, hid, pmw3389, scroll_A, scroll_B, dpi_button, 
+            forward_button, backward_button, led_red, led_blue, led_green) 
+            = (ctx.resources.left_button, ctx.resources.right_button,ctx.resources.scroll_button,
+                 ctx.resources.usb_dev, 
+               ctx.resources.hid, ctx.resources.pmw3389, ctx.resources.scroll_A,
+               ctx.resources.scroll_B, ctx.resources.dpi_button, ctx.resources.forward_button, 
+               ctx.resources.backward_button, ctx.resources.led_red, ctx.resources.led_blue, ctx.resources.led_green);
+
+        let mut a:bool = scroll_A.is_high().unwrap();
+        let mut b:bool = scroll_B.is_high().unwrap();
+        *wheel_count = check_scroll(a,b,*a_prev,*b_prev);
+        *a_prev = a;
+        *b_prev = b;
+        
+        // Read from sensor
+        let (x_sensor, y_sensor) = pmw3389.read_status().unwrap();
+        
+        let left:u8;
+        if left_button.is_low().unwrap(){
+            left = 1;
+        }else{
+            left = 0;
+        }
+        let right:u8;
+        if right_button.is_low().unwrap(){
+            right = 2;
+        }else{
+            right = 0;
+        }
+        //This dose not work yet.
+        let scroll:u8;
+        if scroll_button.is_low().unwrap(){
+            scroll = 4;
+        }else{
+            scroll = 0;
+        }
+
+
+        if forward_button.is_high().unwrap() && *forward_button_pressed == false{
+            *wrapping_led_counter = *wrapping_led_counter + 1;
+            rprintln!("{}", wrapping_led_counter);
+        }
+        if backward_button.is_high().unwrap() && *backward_button_pressed == false{
+            *wrapping_led_counter = *wrapping_led_counter - 1;
+            rprintln!("{}", wrapping_led_counter);
+        }
+
+        
+
+        if *wrapping_led_counter & 1 !=0{
+            led_blue.set_high().ok();
+        }else{
+            led_blue.set_low().ok();
+
+        }
+
+        if *wrapping_led_counter & 2 !=0{
+            led_green.set_high().ok();
+        }else{
+            led_green.set_low().ok();
+
+        }
+
+
+        if *wrapping_led_counter & 4 !=0{
+            led_red.set_high().ok();
+        }else{
+            led_red.set_low().ok();
+
+        }
+
+
+        *forward_button_pressed = forward_button.is_high().unwrap();
+        *backward_button_pressed = backward_button.is_high().unwrap();
+
+        //rprintln!("{}",dpi_button.is_low().unwrap());
+        let dpi:i8;
+        let mut length:i8 = dpi_settings.len() as i8;
+        //rprintln!("lenght: {}, Index: {}, DPI: {}",length,*dpi_toggle, dpi_settings[*dpi_toggle as usize]);
+        //let temp_dpi: bool = dpi_button_prev;
+        if dpi_button.is_high().unwrap() && *dpi_button_prev == false{
+
+            if *dpi_toggle +1  < length  {
+                *dpi_toggle = *dpi_toggle +1;
+                //rprintln!("{}",dpi_settings[*dpi_toggle as usize]);
+
+            } else {
+                *dpi_toggle = 0;
+            }
+
+            
+        }
+       
+        *dpi_button_prev = dpi_button.is_high().unwrap();        
+ 
+        let mut index:usize = *dpi_toggle as usize;
+        //https://eleccelerator.com/tutorial-about-usb-hid-report-descriptors/
+        let report = MouseReport {
+            x: (x_sensor as i8)/dpi_settings[*dpi_toggle as usize], // need to convert form i16 to i8
+            y: (y_sensor as i8)/dpi_settings[*dpi_toggle as usize], // need to convert form i16 to i8
+            buttons: left+right, // (into takes a bool into an integer)
+            wheel: *wheel_count,
+        };
+
+        // push the report
+        hid.push_input(&report).ok();
+
+        // update the usb device state
+        if usb_dev.poll(&mut [hid]) {
+            return;
+        }
+    }
+
+    #[idle]
+    fn idle(_cx: idle::Context) -> ! {
+        rprintln!("idle");
+        loop {
+            continue;
+        }
+    }
+};
+
+fn check_scroll(scroll_A:bool, scroll_B:bool, scroll_A_prev:bool, scroll_B_prev:bool) -> i8{
+    let mut wheel_count: i8 = 0;
+
+    if scroll_A != scroll_A_prev || scroll_B != scroll_B_prev{
+
+        //Sequence for up:
+        //A:Low  B:Low
+        //A:High B:Low
+        //B:High B:High
+        //A:Low  B:High
+        //A:Low  B:Low
+
+        //Sequence for down:
+        //A:Low  B:Low
+        //A:Low  B:High
+        //A:High B:High
+        //A:High B:Low
+        //A:Low  B:Low
+
+        if scroll_A_prev==scroll_B_prev{
+            if scroll_B==scroll_B_prev{
+                wheel_count +=1;
+                rprintln!("Up count:{}", wheel_count)
+            }else{
+                wheel_count -=1;
+                rprintln!("Down count:{}", wheel_count)
+            }
+        }else{
+            if scroll_A==scroll_A_prev{
+                wheel_count +=1;
+                rprintln!("Up count:{}", wheel_count)
+            }else{
+                wheel_count -=1;
+                rprintln!("Down count:{}", wheel_count)
+            }
+        }
+    }
+    return wheel_count;
+}
diff --git a/src/main.rs b/src/main.rs
index 792259654a49249056b0368a6cc45d2f3959069e..1d4474b3e58a67f33189883fea05072d9708d169 100644
--- a/src/main.rs
+++ b/src/main.rs
@@ -1,20 +1,418 @@
-#![no_std]
+//Work made by J, Jacobsson, T. Andersson and S. Gradén.
+//Tested and valideted on:
+//Windows - Lenovo Yoga 7 series
+//Mac - Apple MacBook Pro Model A2141 EMC 3347
+//TODO:
+//Forward and back buttons should work as normal buttons.
+//RGB should be able to be configured in the computer.
+
 #![no_main]
+#![no_std]
+
+//Needed to create custom made hid reports
+use usbd_hid::hid_class::HIDClass;
+use usbd_hid::descriptor::SerializedDescriptor;
+use serde::ser::{Serialize, Serializer, SerializeTuple};
+use usbd_hid::descriptor::AsInputReport;
+use usbd_hid::descriptor::gen_hid_descriptor;
+
+//Cortex things from per
+//use cortex_m::{asm::delay, peripheral::DWT};
+use stm32f4xx_hal::{
+    //dwt::Dwt,
+    gpio::Speed,
+    //Look at resources to see what pin belongs to what.
+    gpio::{gpioa::{PA1, PA2, PA3, PA4, PA5, PA6, PA7},
+        gpiob::{PB10, PB12, PB14,PB15},
+        gpioc::{PC2, PC3, PC4, PC5},
+        Alternate, Output, PushPull, Input, PullDown,// PullUp, 
+    },
+    //rcc::Clocks,
+    spi::Spi,
+    //stm32,
+    otg_fs::{UsbBus, UsbBusType, USB}, //USB
+    prelude::*,
+};
+use usb_device::{bus::UsbBusAllocator, prelude::*};
+
+use embedded_hal::spi::MODE_3;
+//use rtic::cyccnt::{Instant, U32Ext as _};
+use panic_rtt_target as _;
+use rtt_target::{rprintln, rtt_init_print};
+
+use app::{
+    pmw3389::{self, Register},
+    DwtDelay,
+};
+
+//Some settings for the sensor.
+type PMW3389T = pmw3389::Pmw3389<
+    Spi<
+        stm32f4xx_hal::stm32::SPI2,
+        (
+            PB10<Alternate<stm32f4xx_hal::gpio::AF5>>,
+            PC2<Alternate<stm32f4xx_hal::gpio::AF5>>,
+            PC3<Alternate<stm32f4xx_hal::gpio::AF5>>,
+        ),
+    >,
+    PB12<Output<PushPull>>,
+>;
+
+//Report for USB.
+#[gen_hid_descriptor(
+    (collection = APPLICATION, usage_page = GENERIC_DESKTOP, usage = MOUSE) = {
+        (collection = PHYSICAL, usage = POINTER) = {
+            (usage_page = BUTTON, usage_min = 0x01, usage_max = 0x05) = {
+                #[packed_bits 5] #[item_settings data,variable,absolute] buttons=input;
+            };
+            (usage_page = GENERIC_DESKTOP,) = {
+                (usage = X,) = {
+                    #[item_settings data,variable,relative] x=input;
+                };
+                (usage = Y,) = {
+                    #[item_settings data,variable,relative] y=input;
+                };
+                (usage = WHEEL,) = {
+                    #[item_settings data,variable,relative] wheel=input;
+                };
+            };
+        };
+    }
+)]
+pub struct NuttaliReport {
+    pub buttons: u8,
+    pub x: i8,
+    pub y: i8,
+    pub wheel: i8, // Scroll down (negative) or up (positive) this many units
+}
+
+#[rtic::app(device = stm32f4xx_hal::stm32, peripherals = true)]
+const APP: () = {
+    struct Resources {
+        // late resources
+        // Leds
+        led_blue: PA1<Output<PushPull>>,
+        led_red:  PA3<Output<PushPull>>,
+        led_green: PA2<Output<PushPull>>,
+
+        // Buttons
+        dpi_button: PA4<Input<PullDown>>,
+        right_button: PA5<Input<PullDown>>,
+        scroll_button: PA6<Input<PullDown>>,
+        backward_button: PB15<Input<PullDown>>,
+        forward_button: PB14<Input<PullDown>>,
+        left_button: PC5<Input<PullDown>>,
+
+        // Scroll
+        scroll_B: PC4<Input<PullDown>>,
+        scroll_A: PA7<Input<PullDown>>,
+
+        // USB
+        hid: HIDClass<'static, UsbBusType>,
+        usb_dev: UsbDevice<'static, UsbBus<USB>>,
+        
+        //Sensor
+        pmw3389: PMW3389T, 
+    }
+
+    #[init]
+    fn init(mut ctx: init::Context) -> init::LateResources {
+        static mut EP_MEMORY: [u32; 1024] = [0; 1024];
+        static mut USB_BUS: Option<UsbBusAllocator<UsbBusType>> = None;
+
+        rtt_init_print!();
+        rprintln!("init");
+        
+        //Split all needed gpioa so that we can access every single pin.
+        let gpioa = ctx.device.GPIOA.split();
+        let gpiob = ctx.device.GPIOB.split();
+        let gpioc = ctx.device.GPIOC.split();
+
+        // Set up the system clock.
+        let rcc = ctx.device.RCC.constrain();
+        let _clocks = rcc.cfgr.sysclk(48.mhz()).require_pll48clk().freeze();
+
+        // Initialize (enable) the monotonic timer (CYCCNT)
+        ctx.core.DCB.enable_trace();
+        ctx.core.DWT.enable_cycle_counter();
+
+        // Leds
+        let led_red = gpioa.pa3.into_push_pull_output();
+        let led_green = gpioa.pa2.into_push_pull_output();
+        let led_blue = gpioa.pa1.into_push_pull_output();
+        
+        // Buttons
+        let left_button = gpioc.pc5.into_pull_down_input();
+        let right_button = gpioa.pa5.into_pull_down_input();
+        let scroll_button = gpioa.pa6.into_pull_down_input();
+        let backward_button = gpiob.pb15.into_pull_down_input();
+        let forward_button = gpiob.pb14.into_pull_down_input();
+        let dpi_button = gpioa.pa4.into_pull_down_input();
+
+        //Scroll
+        let scroll_A = gpioa.pa7.into_pull_down_input();
+        let scroll_B = gpioc.pc4.into_pull_down_input();
+
+        // Sensor Init
+        // ||||||||||
+        // \/\/\/\/\/
+        let mut core = ctx.core;
+
+        // Initialize (enable) the monotonic timer (CYCCNT)
+        core.DCB.enable_trace();
+        core.DWT.enable_cycle_counter();
+
+        // setup clocks Duplicate code
+        //let rcc = ctx.device.RCC.constrain();
+        //let clocks = rcc.cfgr.freeze();
+        rprintln!("clocks:");
+        rprintln!("hclk {}", _clocks.hclk().0);
+
+        // Configure SPI
+        let sck = gpiob.pb10.into_alternate_af5();
+        let miso = gpioc.pc2.into_alternate_af5();
+        let mosi = gpioc.pc3.into_alternate_af5();
+        let cs = gpiob.pb12.into_push_pull_output().set_speed(Speed::High);
+
+        let spi = Spi::spi2(
+            ctx.device.SPI2,
+            (sck, miso, mosi),
+            MODE_3,
+            stm32f4xx_hal::time::KiloHertz(2000).into(),
+            _clocks,
+        );
 
-// pick a panicking behavior
-use panic_halt as _; // you can put a breakpoint on `rust_begin_unwind` to catch panics
-// use panic_abort as _; // requires nightly
-// use panic_itm as _; // logs messages over ITM; requires ITM support
-// use panic_semihosting as _; // logs messages to the host stderr; requires a debugger
+        let delay_or_something = DwtDelay::new(&mut core.DWT, _clocks);
+        let mut pmw3389 = pmw3389::Pmw3389::new(spi, cs, delay_or_something).unwrap();
 
-use cortex_m::asm;
-use cortex_m_rt::entry;
+        // set in burst mode
+        let _burst = pmw3389.write_register(Register::MotionBurst, 0x00);
+        // /\/\/\/\/\
+        // ||||||||||
+        // Sensor Init
+
+        // USB
+        // ||||||||||
+        // \/\/\/\/\/
+
+        // Pull the D+ pin down to send a RESET condition to the USB bus.
+        // Dose not work yet.
+        //let mut usb_dp = gpioa.pa12.into_alternate_af10();
+        //usb_dp= false;
+        //delay(_clocks.sysclk().0 / 100);
+
+        let usb = USB {
+            usb_global: ctx.device.OTG_FS_GLOBAL,
+            usb_device: ctx.device.OTG_FS_DEVICE,
+            usb_pwrclk: ctx.device.OTG_FS_PWRCLK,
+            pin_dm: gpioa.pa11.into_alternate_af10(),
+            pin_dp: gpioa.pa12.into_alternate_af10(),
+        };
+
+        USB_BUS.replace(UsbBus::new(usb, EP_MEMORY));
+        
+        let hid = HIDClass::new(USB_BUS.as_ref().unwrap(), NuttaliReport::desc(), 1);
+        let usb_dev = UsbDeviceBuilder::new(USB_BUS.as_ref().unwrap(), UsbVidPid(0xc410, 0x0000))
+            .manufacturer("Nuttali")
+            .product("Mouse")
+            .serial_number("1.0")
+            .device_class(0)
+            .build();
+        
+        // /\/\/\/\/\
+        // ||||||||||
+        // USB
+        
+        init::LateResources{led_blue, led_red, led_green, dpi_button, left_button, right_button, scroll_button, backward_button, forward_button, hid, usb_dev, pmw3389, scroll_B, scroll_A}
+    }
+
+    #[task(binds=OTG_FS, resources = [led_blue, led_red, led_green, dpi_button, left_button, right_button, scroll_button, backward_button, forward_button, hid, usb_dev, pmw3389, scroll_A, scroll_B])]
+    fn on_usb(ctx: on_usb::Context) {
+        //The scroll wheel need to know the last position or dose not work.
+        static mut A_PREV :bool = false;
+        static mut B_PREV :bool = false;
+        
+        
+        static mut DPI_BUTTON_PREV: bool = false;
+        
+        static mut WRAPPING_LED_COUNTER:i32 = 0;
+        
+        // destruct the context
+        let (led_blue, led_red, led_green, dpi_button,
+            left_button, right_button, scroll_button, backward_button, 
+            forward_button, usb_dev, hid, pmw3389, scroll_A, scroll_B) 
+            = (ctx.resources.led_blue,ctx.resources.led_red,
+               ctx.resources.led_green,ctx.resources.dpi_button,
+               ctx.resources.left_button, ctx.resources.right_button,
+               ctx.resources.scroll_button, ctx.resources.backward_button,
+               ctx.resources.forward_button, ctx.resources.usb_dev, 
+               ctx.resources.hid, ctx.resources.pmw3389, ctx.resources.scroll_A,
+               ctx.resources.scroll_B);
+        let a:bool = scroll_A.is_high().unwrap();
+        let b:bool = scroll_B.is_high().unwrap();
+        let wheel_count = check_scroll(a,b,*A_PREV,*B_PREV);
+        *A_PREV = a;
+        *B_PREV = b;
+        
+        // Read from sensor
+        let (x_sensor, y_sensor) = pmw3389.read_status().unwrap();
+        
+        let left:bool = left_button.is_low().unwrap();
+        let right:bool = right_button.is_low().unwrap();
+        let scroll:bool = scroll_button.is_high().unwrap();
+        let backward:bool = backward_button.is_high().unwrap();
+        let forward:bool = forward_button.is_high().unwrap();
+
+        let report = NuttaliReport {
+            x: (x_sensor as i8)>> 1, // need to convert form i16 to i8. Shifts to get smother movement
+            y: (y_sensor as i8)>> 1, // need to convert form i16 to i8. Shifts to get smother movement
+            buttons: check_buttons(left, right, scroll, backward, forward), // (into takes a bool into an integer)
+            wheel: wheel_count,
+        };
+
+        
+        if dpi_button.is_high().unwrap() && *DPI_BUTTON_PREV == false{
+            *WRAPPING_LED_COUNTER = *WRAPPING_LED_COUNTER + 1;
+            let (red,blue,green) = change_led(*WRAPPING_LED_COUNTER);
+            if red{
+                led_red.set_high().ok();
+            }else{
+                led_red.set_low().ok();
+            }
+            if blue{
+                led_blue.set_high().ok();
+            }else{
+                led_blue.set_low().ok();
+            }
+            if green{
+                led_green.set_high().ok();
+            }else{
+                led_green.set_low().ok();
+            }
+        }
+        *DPI_BUTTON_PREV = dpi_button.is_high().unwrap();
+
+        // push the report
+        hid.push_input(&report).ok();
+
+        // update the usb device state
+        if usb_dev.poll(&mut [hid]) {
+            return;
+        }
+    }
+
+    #[idle]
+    fn idle(_cx: idle::Context) -> ! {
+        rprintln!("idle");
+        loop {
+            continue;
+        }
+    }
+};
+
+fn check_scroll(scroll_a:bool, scroll_b:bool, scroll_a_prev:bool, scroll_b_prev:bool) -> i8{
+    let mut wheel_count: i8 = 0;
+
+    if scroll_a != scroll_a_prev || scroll_b != scroll_b_prev{
+
+        //Sequence for up:
+        //A:Low  B:Low
+        //A:High B:Low
+        //B:High B:High
+        //A:Low  B:High
+        //A:Low  B:Low
+
+        //Sequence for down:
+        //A:Low  B:Low
+        //A:Low  B:High
+        //A:High B:High
+        //A:High B:Low
+        //A:Low  B:Low
+
+        if scroll_a_prev==scroll_b_prev{
+            if scroll_b==scroll_b_prev{
+                wheel_count +=1;
+                rprintln!("Up count:{}", wheel_count)
+            }else{
+                wheel_count -=1;
+                rprintln!("Down count:{}", wheel_count)
+            }
+        }else{
+            if scroll_a==scroll_a_prev{
+                wheel_count +=1;
+                rprintln!("Up count:{}", wheel_count)
+            }else{
+                wheel_count -=1;
+                rprintln!("Down count:{}", wheel_count)
+            }
+        }
+    }
+    return wheel_count;
+}
+
+//Dose not check dpi
+// Left button : bit no 0
+// Right button : bit no 1
+// Scroll/Middle button : bit no 2
+// Backward button : bit no 3
+// Forward button : bit no 4
+fn check_buttons(left:bool,right:bool,scroll:bool,backward:bool,forward:bool) -> u8{
+    let mut result:u8 = 0;
+    if left{
+        result += 1;
+    }
+    if right{
+        result += 2;
+    }
+    if scroll{
+        result += 4;
+    }
+    if backward{
+        result += 8;
+    }
+    if forward{ 
+        result += 16;
+    }
+    return result;
+}
 
-#[entry]
-fn main() -> ! {
-    asm::nop(); // To not have main optimize to abort in release mode, remove when you add code
+fn change_led(no_toggled: i32) -> (bool,bool,bool) {
+    let led_red:bool;
+    let led_blue:bool;
+    let led_green:bool;
 
-    loop {
-        // your code goes here
+    if no_toggled % 8 == 0{
+        led_red= true;
+        led_green= true;
+        led_blue= true;
+    } else if no_toggled % 8 == 1{
+        led_red= true;
+        led_blue= false;
+        led_green= true;
+    } else if no_toggled % 8 == 2{
+        led_red= true;
+        led_blue= true;
+        led_green= false;
+    } else if no_toggled % 8 == 3{
+        led_red= false;
+        led_blue= true;
+        led_green= true;
+    } else if no_toggled % 8 == 4{
+        led_red= true;
+        led_blue= false;
+        led_green= false;
+    } else if no_toggled % 8 == 5{
+        led_red= false;
+        led_blue= false;
+        led_green= true;
+    } else if no_toggled % 8 == 6{
+        led_red= false;
+        led_blue= true;
+        led_green= false;
+    } else {
+        led_red= false;
+        led_blue= false;
+        led_green= false;
     }
+    return (led_red,led_blue,led_green);
 }