Compare commits
8 commits
45db5e8af8
...
d053f8d080
| Author | SHA1 | Date | |
|---|---|---|---|
| d053f8d080 | |||
| f26920a099 | |||
| 60d6aaecd6 | |||
| 10a38f9bbc | |||
| 5934336984 | |||
| f3ac43614c | |||
| b6fa0e3b2d | |||
| cd91b3f540 |
4 changed files with 159 additions and 86 deletions
|
|
@ -1 +1 @@
|
|||
Subproject commit f41336744c4e2548c8f6ba9b323ae4aa39959f1d
|
||||
Subproject commit 4f11d68e62dcb0e7098eecf357168724a8322d80
|
||||
|
|
@ -9,7 +9,7 @@ pub enum State {
|
|||
Active,
|
||||
}
|
||||
|
||||
mod settings {
|
||||
pub mod settings {
|
||||
|
||||
#[derive(Debug, Default, Clone, Copy)]
|
||||
pub enum Level {
|
||||
|
|
@ -333,10 +333,11 @@ impl App {
|
|||
services: Services,
|
||||
sequences: Sequences,
|
||||
interfaces: Interfaces,
|
||||
settings: Settings,
|
||||
) -> Self {
|
||||
Self {
|
||||
state: State::default(),
|
||||
settings: Settings::default(),
|
||||
settings,
|
||||
timers: Timers::new(config.timers, config.system_tick_rate_hz),
|
||||
services,
|
||||
sequences,
|
||||
|
|
@ -346,6 +347,8 @@ impl App {
|
|||
|
||||
pub fn init(&mut self) {
|
||||
// self.timers.init();
|
||||
self.interfaces.amp.enable();
|
||||
|
||||
self.timers.batt_adc_timer.reset();
|
||||
self.timers.batt_adc_timer.enable(true);
|
||||
|
||||
|
|
@ -367,10 +370,11 @@ impl App {
|
|||
// self.timers.led2_timer.reset();
|
||||
// self.timers.led2_timer.enable(true);
|
||||
|
||||
self.services.synth0.set_freq(1);
|
||||
// self.services.synth0.set_freq(1);
|
||||
self.services.synth0.disable();
|
||||
|
||||
self.services.sequencer.disable();
|
||||
|
||||
crate::riscv::asm::delay(2_500_000);
|
||||
}
|
||||
|
||||
pub fn set_state(&mut self, state: State) {
|
||||
|
|
@ -519,14 +523,10 @@ impl App {
|
|||
} else {
|
||||
self.services.sequencer.disable();
|
||||
self.services.synth0.disable();
|
||||
self.interfaces.amp.disable();
|
||||
}
|
||||
}
|
||||
|
||||
if self.services.synth0.need_service() {
|
||||
if !self.interfaces.amp.enabled() {
|
||||
self.interfaces.amp.enable();
|
||||
}
|
||||
let out = match self.services.synth0.service() {
|
||||
Some(value) => value / 6 / self.settings.volume.as_volume_divisor(),
|
||||
None => 0,
|
||||
|
|
@ -555,12 +555,11 @@ impl App {
|
|||
self.interfaces
|
||||
.pwm_core
|
||||
.write_amplitude(self.services.led1.channel, 0);
|
||||
// self.interfaces
|
||||
// .pwm_core
|
||||
// .write_amplitude(self.services.led2.channel, 0);
|
||||
self.interfaces
|
||||
.pwm_core
|
||||
.disable(ch32_hal::timer::Channel::Ch4);
|
||||
crate::riscv::asm::delay(10_000_000);
|
||||
|
||||
self.interfaces.pwm_core.pwm.borrow().shutdown();
|
||||
self.interfaces.adc_core.shutdown();
|
||||
|
||||
self.interfaces.amp.disable();
|
||||
}
|
||||
pub fn volume_button(&mut self) {
|
||||
|
|
@ -625,7 +624,7 @@ impl App {
|
|||
|
||||
// Events
|
||||
impl App {
|
||||
fn main_button_click(&mut self) {
|
||||
pub fn main_button_click(&mut self) {
|
||||
// TODO
|
||||
#[cfg(feature = "enable_print")]
|
||||
println!("click");
|
||||
|
|
@ -661,6 +660,9 @@ impl App {
|
|||
pub fn get_state(&self) -> State {
|
||||
self.state
|
||||
}
|
||||
pub fn get_settings(&self) -> Settings {
|
||||
self.settings
|
||||
}
|
||||
pub fn should_wake(&self) -> bool {
|
||||
if self.interfaces.usb.powered() {
|
||||
return true;
|
||||
|
|
|
|||
|
|
@ -11,7 +11,7 @@ use crate::insert_coin::services::{DacService, LedService, Service, TickService,
|
|||
// static LED1_DCS: [u8; 5] = [0u8, 25u8, 50u8, 75u8, 100u8];
|
||||
|
||||
pub struct SimplePwmCore<'d, T: GeneralInstance16bit> {
|
||||
pwm: core::cell::RefCell<SimplePwm<'d, T>>,
|
||||
pub pwm: core::cell::RefCell<SimplePwm<'d, T>>,
|
||||
}
|
||||
|
||||
impl<'d, T: GeneralInstance16bit> SimplePwmCore<'d, T> {
|
||||
|
|
|
|||
|
|
@ -126,6 +126,10 @@ impl AdcCore {
|
|||
}
|
||||
sum / self.batt_values.len() as u16
|
||||
}
|
||||
|
||||
pub fn shutdown(&mut self) {
|
||||
self.adc.shutdown()
|
||||
}
|
||||
}
|
||||
|
||||
#[derive(Debug)]
|
||||
|
|
@ -241,10 +245,20 @@ bind_interrupts!(struct Irqs {
|
|||
});
|
||||
|
||||
// TODO: remove
|
||||
use app::settings::Settings;
|
||||
use insert_coin::TickTimerService;
|
||||
use insert_coin::{TickService, TickServiceData};
|
||||
|
||||
fn app_main(mut p: hal::Peripherals) -> ! {
|
||||
fn app_main(mut p: hal::Peripherals, app_settings: Settings) -> Settings {
|
||||
// initialize ADC core first, and exit if battery is too low
|
||||
let mut adc = hal::adc::Adc::new(p.ADC1, Default::default());
|
||||
let mut batt_monitor_pin = p.PD4;
|
||||
let mut adc_core = AdcCore::new(adc, batt_monitor_pin);
|
||||
let bv = adc_core.get_battery_voltage();
|
||||
if bv < 421 {
|
||||
adc_core.shutdown();
|
||||
return app_settings;
|
||||
}
|
||||
// === output setup ===
|
||||
|
||||
// LED0 output setup
|
||||
|
|
@ -255,10 +269,6 @@ fn app_main(mut p: hal::Peripherals) -> ! {
|
|||
let led1_pin = PwmPin::new_ch1::<0>(p.PD2);
|
||||
let led1_ch = hal::timer::Channel::Ch1;
|
||||
|
||||
// // LED2 output setup
|
||||
// let led2_pin = PwmPin::new_ch2::<0>(p.PA1);
|
||||
// let led2_ch = hal::timer::Channel::Ch2;
|
||||
|
||||
// DAC output setup
|
||||
let dac_pin = PwmPin::new_ch4::<0>(p.PC4);
|
||||
// let dac_ch = hal::timer::Channel::Ch4;
|
||||
|
|
@ -277,20 +287,22 @@ fn app_main(mut p: hal::Peripherals) -> ! {
|
|||
|
||||
pwm.set_polarity(led0_ch, OutputPolarity::ActiveHigh);
|
||||
pwm.set_polarity(led1_ch, OutputPolarity::ActiveLow);
|
||||
let mut pwm_core = SimplePwmCore::new(pwm);
|
||||
pwm_core.write_amplitude(led0_ch, 0);
|
||||
pwm_core.write_amplitude(led1_ch, 0);
|
||||
|
||||
// pwm.set_polarity(led2_ch, OutputPolarity::ActiveLow);
|
||||
|
||||
let tick_rate_hz = 50000;
|
||||
|
||||
let core_config = CoreConfig::new(tick_rate_hz);
|
||||
|
||||
let pwm_core = SimplePwmCore::new(pwm);
|
||||
|
||||
// === input setup ===
|
||||
|
||||
// adc
|
||||
let mut adc = hal::adc::Adc::new(p.ADC1, Default::default());
|
||||
let mut batt_monitor_pin = p.PD4;
|
||||
let adc_core = AdcCore::new(adc, batt_monitor_pin);
|
||||
// let mut adc = hal::adc::Adc::new(p.ADC1, Default::default());
|
||||
// let mut batt_monitor_pin = p.PD4;
|
||||
// let adc_core = AdcCore::new(adc, batt_monitor_pin);
|
||||
|
||||
// adc2
|
||||
// let mut usb_detect_dc = hal::adc::Adc::new(p.ADC1, Default::default());
|
||||
|
|
@ -309,8 +321,8 @@ fn app_main(mut p: hal::Peripherals) -> ! {
|
|||
let volume_btn_pin = p.PC6;
|
||||
let light_ctrl_btn_pin = p.PC7;
|
||||
let amp_en = p.PC5;
|
||||
let extra_io_1 = p.PD0;
|
||||
let extra_io_2 = p.PD3;
|
||||
// let extra_io_1 = p.PD0;
|
||||
// let extra_io_2 = p.PD3;
|
||||
|
||||
let mut amp_en_output = OutputOpenDrain::new(amp_en, Level::Low, Default::default());
|
||||
let amp = Amplifier::new(amp_en_output);
|
||||
|
|
@ -340,7 +352,8 @@ fn app_main(mut p: hal::Peripherals) -> ! {
|
|||
led0_timer_ms: 100,
|
||||
led1_timer_ms: 100,
|
||||
// 4 hours:
|
||||
shutdown_timer_s: 4 * 60 * 60,
|
||||
// shutdown_timer_s: 1,
|
||||
shutdown_timer_s: 4 * 60 * 60 * 30 / 100,
|
||||
// led2_timer_ms: 100,
|
||||
};
|
||||
|
||||
|
|
@ -385,7 +398,24 @@ fn app_main(mut p: hal::Peripherals) -> ! {
|
|||
usb,
|
||||
};
|
||||
|
||||
let mut app = App::new(app_config, app_services, app_sequences, app_interfaces);
|
||||
let mut app = App::new(
|
||||
app_config,
|
||||
app_services,
|
||||
app_sequences,
|
||||
app_interfaces,
|
||||
app_settings,
|
||||
);
|
||||
|
||||
let need_sound = unsafe {
|
||||
#[allow(static_mut_refs)]
|
||||
if INPUT_FLAGS.main_btn_flag.active() {
|
||||
#[allow(static_mut_refs)]
|
||||
INPUT_FLAGS.main_btn_flag.clear();
|
||||
true
|
||||
} else {
|
||||
false
|
||||
}
|
||||
};
|
||||
|
||||
// init systick
|
||||
systick_init(tick_rate_hz);
|
||||
|
|
@ -418,6 +448,9 @@ fn app_main(mut p: hal::Peripherals) -> ! {
|
|||
let mut light_ctrl_btn_prev = light_ctrl_btn_input.is_high_immediate();
|
||||
|
||||
app.init();
|
||||
if need_sound {
|
||||
app.main_button_click();
|
||||
}
|
||||
loop {
|
||||
// system servicing
|
||||
|
||||
|
|
@ -516,66 +549,90 @@ fn app_main(mut p: hal::Peripherals) -> ! {
|
|||
// enter standby
|
||||
app::State::DeepSleep => {
|
||||
app.shut_down();
|
||||
|
||||
loop {
|
||||
unsafe {
|
||||
#[allow(static_mut_refs)]
|
||||
INPUT_FLAGS.sense_coin_flag.clear();
|
||||
#[allow(static_mut_refs)]
|
||||
INPUT_FLAGS.main_btn_flag.clear();
|
||||
}
|
||||
unsafe { system::enter_standby() };
|
||||
riscv::asm::wfi();
|
||||
let mut config = hal::Config::default();
|
||||
config.rcc = hal::rcc::Config::SYSCLK_FREQ_48MHZ_HSI;
|
||||
unsafe {
|
||||
hal::rcc::init(config.rcc);
|
||||
}
|
||||
unsafe {
|
||||
#[allow(static_mut_refs)]
|
||||
if (INPUT_FLAGS.sense_coin_flag.active()
|
||||
|| (INPUT_FLAGS.main_btn_flag.active()
|
||||
&& main_btn_input.is_high_immediate()))
|
||||
&& app.should_wake()
|
||||
{
|
||||
unsafe {
|
||||
use hal::pac::Interrupt;
|
||||
use qingke::interrupt::Priority;
|
||||
use qingke_rt::CoreInterrupt;
|
||||
|
||||
system::clear_interrupt(2, 6);
|
||||
|
||||
qingke::pfic::set_priority(
|
||||
CoreInterrupt::SysTick as u8,
|
||||
Priority::P15 as u8,
|
||||
);
|
||||
|
||||
qingke::pfic::enable_interrupt(Interrupt::EXTI7_0 as u8);
|
||||
qingke::pfic::enable_interrupt(CoreInterrupt::SysTick as u8);
|
||||
}
|
||||
|
||||
app.set_state(State::Active);
|
||||
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
return app.get_settings();
|
||||
}
|
||||
// for everything else, don't do anything
|
||||
_ => {}
|
||||
}
|
||||
}
|
||||
}
|
||||
// // if adc1_timer.need_service() {
|
||||
// // let val = adc.convert(&mut batt_monitor_pin, hal::adc::SampleTime::CYCLES241);
|
||||
// // let val = adc.convert(&mut usb_detect_pin, hal::adc::SampleTime::CYCLES241);
|
||||
// // #[cfg(feature = "enable_print")]
|
||||
// // println!("ADC value: {}", val);
|
||||
|
||||
// // adc1_timer.reset();
|
||||
// // adc1_timer.enable(true);
|
||||
// // }
|
||||
// }
|
||||
use ch32_hal::timer::low_level::{OutputCompareMode, Timer};
|
||||
use ch32_hal::timer::Channel;
|
||||
|
||||
// fn shutdown_main(p: Peripherals) {
|
||||
fn shutdown_main(p: hal::Peripherals) {
|
||||
// LED0 output setup
|
||||
let led0_pin = OutputOpenDrain::new(p.PC3, Level::Low, Default::default());
|
||||
let led1_pin = OutputOpenDrain::new(p.PD2, Level::High, Default::default());
|
||||
let led2_pin = OutputOpenDrain::new(p.PA1, Level::High, Default::default());
|
||||
let dac_pin = OutputOpenDrain::new(p.PC4, Level::Low, Default::default());
|
||||
let mut amp_pin = OutputOpenDrain::new(p.PC5, Level::Low, Default::default());
|
||||
amp_pin.set_high();
|
||||
let volume_btn_pin = OutputOpenDrain::new(p.PC6, Level::Low, Default::default());
|
||||
let light_ctrl_btn_pin = OutputOpenDrain::new(p.PC7, Level::Low, Default::default());
|
||||
let usb_detect_input = OutputOpenDrain::new(p.PD5, Level::Low, Default::default());
|
||||
|
||||
let sense_coin_pin = p.PC2;
|
||||
let main_btn_pin = p.PD6;
|
||||
|
||||
unsafe { system::init_gpio_irq(sense_coin_pin.pin(), sense_coin_pin.port(), true, false) };
|
||||
unsafe { system::init_gpio_irq(main_btn_pin.pin(), main_btn_pin.port(), true, false) };
|
||||
|
||||
let sense_coin_pin = Input::new(sense_coin_pin, Pull::None);
|
||||
let main_btn_pin = Input::new(main_btn_pin, Pull::None);
|
||||
|
||||
riscv::asm::delay(1_000_000);
|
||||
|
||||
loop {
|
||||
unsafe { system::enter_standby() };
|
||||
riscv::asm::wfi();
|
||||
unsafe {
|
||||
#[allow(static_mut_refs)]
|
||||
if (INPUT_FLAGS.sense_coin_flag.active() || INPUT_FLAGS.main_btn_flag.active())
|
||||
// && app.should_wake()
|
||||
{
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
// loop {
|
||||
// unsafe {
|
||||
// #[allow(static_mut_refs)]
|
||||
// INPUT_FLAGS.sense_coin_flag.clear();
|
||||
// #[allow(static_mut_refs)]
|
||||
// INPUT_FLAGS.main_btn_flag.clear();
|
||||
// }
|
||||
// unsafe { system::enter_standby() };
|
||||
// riscv::asm::wfi();
|
||||
// unsafe {
|
||||
// #[allow(static_mut_refs)]
|
||||
// if (INPUT_FLAGS.sense_coin_flag.active()
|
||||
// || (INPUT_FLAGS.main_btn_flag.active() && main_btn_input.is_high_immediate()))
|
||||
// && app.should_wake()
|
||||
// {
|
||||
// break;
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
// let mut config = hal::Config::default();
|
||||
// config.rcc = hal::rcc::Config::SYSCLK_FREQ_48MHZ_HSI;
|
||||
// unsafe {
|
||||
// hal::rcc::init(config.rcc);
|
||||
// }
|
||||
// unsafe {
|
||||
// use hal::pac::Interrupt;
|
||||
// use qingke::interrupt::Priority;
|
||||
// use qingke_rt::CoreInterrupt;
|
||||
|
||||
// system::clear_interrupt(2, 6);
|
||||
|
||||
// qingke::pfic::set_priority(CoreInterrupt::SysTick as u8, Priority::P15 as u8);
|
||||
|
||||
// qingke::pfic::enable_interrupt(Interrupt::EXTI7_0 as u8);
|
||||
// qingke::pfic::enable_interrupt(CoreInterrupt::SysTick as u8);
|
||||
// }
|
||||
}
|
||||
|
||||
#[qingke_rt::entry]
|
||||
fn main() -> ! {
|
||||
|
|
@ -592,7 +649,21 @@ fn main() -> ! {
|
|||
// println!("post");
|
||||
// debug_main(p);
|
||||
|
||||
app_main(p);
|
||||
let mut app_settings = Settings::default();
|
||||
|
||||
loop {
|
||||
unsafe {
|
||||
hal::rcc::init(hal::rcc::Config::SYSCLK_FREQ_48MHZ_HSI);
|
||||
}
|
||||
let mut p = unsafe { hal::Peripherals::steal() };
|
||||
app_settings = app_main(p, app_settings);
|
||||
|
||||
unsafe {
|
||||
hal::rcc::init(hal::rcc::Config::SYSCLK_FREQ_48MHZ_HSI);
|
||||
}
|
||||
let mut p = unsafe { hal::Peripherals::steal() };
|
||||
shutdown_main(p);
|
||||
}
|
||||
}
|
||||
|
||||
#[panic_handler]
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue