dc33-retro-tech-addon/firmware/retro_tech_fw/code/main.c
true efaeb803a5 fix various bugs. editor button initial WIP.
setting cursor to off would keep its last state active. fixed.

cursor wouldn't turn off all the way and would glitch out. fixed.

cursor now has a nicer fadeout.

fixed potentiometer scaling factors.

tried fixing clockspeed stuff. with these changes clock speed can more reliably change to 24MHz or 48MHz, but this isn't thoroughly tested. 3MHz to 24MHz was still crashing. as ADC is in use, code would need to be refactored to not change clock speed while ADC is converting. since I don't want to do this right now, this will run at a fixed speed at the expense of 0.5-1mA.

editor buttons working and updated to the new arrangement, but not tested in depth.

pressing and holding to exit parameter editor while edit mode active would result in next entry into parameter editor being in edit mode. fixed.

lsens / stat LED now functioning in program and parameter edit modes.
2025-07-24 16:03:48 -07:00

169 lines
4.7 KiB
C

/*
* RETRO TECH 2025
* GAT Addon Firmware
* by true
*
* version 0.1.1
* Last Update 20250723
*
* code was made for different random addons I designed for dc32,
* then adapted to each one. it worked OK. this code was then more
* or less directly ported to another MCU. so things might be a mess.
*
* I had only a few hours on and off over a week to get the code done.
* lots of shit was copied from demo code and adapted to work. certainly
* isn't the best way to get this done.
*
* I know I could save some power, but seeing as all the badges burn it in
* LEDs and almost nobody else power optimizes their badge code, who cares?
*
* sorry. wasn't procrastination I swear. all the ideas were last minute.
*/
#include <ch32x035.h>
#include <stdint.h>
#include "src/adc.h"
#include "src/btn.h"
#include "src/config.h"
#include "src/i2c_soft.h"
#include "src/led.h"
#include "src/led_rgbprog.h"
#include "src/rand.h"
#include "src/ui.h"
#include "global.h"
void systick_init(void)
{
SysTick->CMP = (SystemCoreClock / 512) - 1; // we want a 512Hz interrupt
SysTick->CNT = 0; // clear counter
SysTick->CTLR = 0xF; // start counter in /1 mode, enable interrupts, auto-reset counter
SysTick->SR = 0; // clear count comparison flag
NVIC_EnableIRQ(SysTicK_IRQn); // enable interrupt
}
void awu_init(void)
{
AWU_SetPrescaler(AWU_Prescaler_2);
AWU_SetWindowValue(47);
AutoWakeUpCmd(ENABLE);
// in order to fire AWU interrupt, enable EXTI interrupt on rising edge on EXTI line 27.
// this isn't explicitly stated in the DS, but AWU interrupt == EXTI line27 interrupt.
EXTI->RTENR = EXTI_RTENR_TR27;
EXTI->INTENR = EXTI_INTENR_MR27;
NVIC_EnableIRQ(AWU_IRQn);
}
void gpio_init()
{
GPIO_InitTypeDef gpio = {0};
// only one GPIO speed on this bad boy
gpio.GPIO_Speed = GPIO_Speed_50MHz;
// jogwheel digital inputs, active low (PA4-PA6)
gpio.GPIO_Mode = GPIO_Mode_IPU;
gpio.GPIO_Pin = GPIO_Pin_4 | GPIO_Pin_5 | GPIO_Pin_6;
GPIO_Init(GPIOA, &gpio);
// lightsense LED cathode (PA7, A8)
gpio.GPIO_Mode = GPIO_Mode_AIN;
gpio.GPIO_Pin = GPIO_Pin_7;
GPIOA->BCR = GPIO_Pin_7;
GPIO_Init(GPIOA, &gpio);
// potentiometer (PB1, A9)
gpio.GPIO_Pin = GPIO_Pin_1;
GPIO_Init(GPIOB, &gpio);
// lightsense LED anode
gpio.GPIO_Mode = GPIO_Mode_Out_PP;
gpio.GPIO_Pin = GPIO_Pin_7;
GPIOB->BCR = GPIO_Pin_7;
GPIO_Init(GPIOB, &gpio);
// USB (unused in application) - PC16, PC17
// debug (not changed in application) - PC18, PC19
// EEP_WP EEPROM write protect (PA9) (active high)
// IS_SDB IS31FL3729 shutdown pin (PC3) (active low)
gpio.GPIO_Mode = GPIO_Mode_Out_PP;
GPIOA->BCR = GPIO_Pin_9;
gpio.GPIO_Pin = GPIO_Pin_9;
GPIO_Init(GPIOA, &gpio);
GPIOC->BCR = GPIO_Pin_3;
gpio.GPIO_Pin = GPIO_Pin_3;
GPIO_Init(GPIOC, &gpio);
// I2C SCL, SCA for addon header
gpio.GPIO_Mode = GPIO_Mode_AF_PP;
gpio.GPIO_Pin = GPIO_Pin_10 | GPIO_Pin_11;
GPIO_Init(GPIOA, &gpio);
// software I2C, SCL for on-board devices
gpio.GPIO_Mode = GPIO_Mode_IN_FLOATING;
GPIOA->BCR = GPIO_Pin_0 | GPIO_Pin_1;
gpio.GPIO_Pin = GPIO_Pin_0 | GPIO_Pin_1;
GPIO_Init(GPIOA, &gpio);
// UART RX/TX on addon header; not currently used
gpio.GPIO_Mode = GPIO_Mode_IPU;
gpio.GPIO_Pin = GPIO_Pin_2 | GPIO_Pin_3;
GPIO_Init(GPIOA, &gpio);
}
int main(void)
{
// configure core
NVIC_PriorityGroupConfig(NVIC_PriorityGroup_1);
// enable peripheral clocks
RCC_APB1PeriphClockCmd( RCC_APB1Periph_PWR | RCC_APB1Periph_I2C1, ENABLE);
RCC_APB2PeriphClockCmd( RCC_APB2Periph_AFIO | RCC_APB2Periph_GPIOA |
RCC_APB2Periph_GPIOB | RCC_APB2Periph_GPIOC |
RCC_APB2Periph_ADC1 | RCC_APB2Periph_TIM1, ENABLE);
// configure gpio pins, hard buttons (used for settings reset)
gpio_init();
// get saved settings, or reset if BTN1 is pushed
i2cm_init();
userconf_load((BTN_PORT->INDR & (1 << BTN2_PIN)) ? 0 : 1);
// configure hardware
adc_init();
btn_init();
led_init();
// configure random
tinymt32_init(&tinymt32_s, DBGMCU_GetCHIPID() | userconf.checksum);
// configure UI
ui_init();
// configure auto-wakeup to run at 498Hz
awu_init();
// set up LEDs initially
led_rgb_firstrun();
// do system shit
while(1) {
__WFI();
// after sending LEDs, run LED render program
// to update the LED buffer for next time
// we have approx 7ms to render... plenty of time
if ((ticnt & 0x3) == 0) {
ui_render();
}
}
}