From e811d778ea51ac1e25588a9cc957fca4f532ea5a Mon Sep 17 00:00:00 2001 From: Brett Weiland Date: Fri, 27 Oct 2023 07:10:26 -0500 Subject: init --- software_pwm.c | 89 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 89 insertions(+) create mode 100644 software_pwm.c (limited to 'software_pwm.c') diff --git a/software_pwm.c b/software_pwm.c new file mode 100644 index 0000000..561edfd --- /dev/null +++ b/software_pwm.c @@ -0,0 +1,89 @@ +#include +#include +#include +#include +#include +#include + +#include "software_pwm.h" +#include "pins.h" + + +static struct link_pair { + struct pwm_event *next; + struct pwm_event *prev; +}; + +//if next is ever zero, node is assumed not part of list/disabled +static struct pwm_event { + struct link_pair active; + struct link_pair twins; + uint8_t time; + uint8_t pins; + bool enabled; +} events[SOFTPWM_PIN_COUNT + 1]; + + +#define LIST_INSERT(new, former, member) (\ + list_insert(&(new.member), &(former.member), offsetof(struct pwm_event, time))) + +static void list_insert(struct link_pair *new_links, struct link_pair *former_links, size_t parent_offset) { + +} + +static void list_remove(struct link_pair *event) { +} + +void init_softpwm() { + + //this one never moves + events[SOFTPWM_PIN_COUNT].time = 0; + events[SOFTPWM_PIN_COUNT].pins = 0; + events[SOFTPWM_PIN_COUNT].active.next = &events[SOFTPWM_PIN_COUNT]; + events[SOFTPWM_PIN_COUNT].active.prev = &events[SOFTPWM_PIN_COUNT]; + events[SOFTPWM_PIN_COUNT].enabled = true; + + //TODO: move all to zero once init_softpwm tested + for(size_t event_i = 0; event_i < SOFTPWM_PIN_COUNT; event_i++) { + events[event_i].time = event_i; + events[event_i].pins = (1 << (event_i + 1)) - 1; + LIST_INSERT(events[event_i], events[((int)event_i - 1) % (SOFTPWM_PIN_COUNT + 1)], active); + } + + SOFTPWM_DDR = 0xff; + + //use external 10mhz clock (we just have one laying around) + //then prescale by 1024. Check at different freqs for brightness + TCCR0A = 0b00000010; + TIMSK0 = 0b00000011; + OCR0A = events[SOFTPWM_PIN_COUNT].time; + TIFR0 = 0b00000010; //interupts enabled! + sei(); +} + +void softpwm_set(uint8_t pin, uint8_t duty) { + /** + struct pwm_event *event_unmoved = &events[pin]; //TODO describe if you want ig + struct pwm_event *this_event = &events[pin]; + this_event->time = duty; + if(duty < events[pin].time) { + while(duty < event_unmoved->time) event_unmoved = event_unmoved->next; + } + else { + } + **/ +} + +/** +ISR(TIMER0_OVF_vect) { +} +**/ + +ISR(TIMER0_COMP_vect) { + /** + static struct pwm_event *on_event = &events[SOFTPWM_PIN_COUNT]; + SOFTPWM_PORT = on_event->pins; + on_event = on_event->next; + OCR0A = on_event->time; + **/ +} -- cgit v1.2.3