/* Implementation of Delta-Sigma modulator support. * * Part of esp-open-rtos * Copyright (C) 2018 ourairquality (https://github.com/ourairquality) * Copyright (C) 2018 Zaltora (https://github.com/Zaltora) * BSD Licensed as described in the file LICENSE */ #include "dsm.h" #include #include #if (DSM_DEBUG) #define debug(fmt, ...) printf("%s: " fmt "\n", "DSM", ## __VA_ARGS__) #else #define debug(fmt, ...) #endif typedef struct dsmInfoDefinition { uint8_t running; uint8_t preScale; uint8_t target; bool output; /* private */ uint8_t usedPins; uint8_t pins[8]; } DSMInfo; static DSMInfo dsmInfo; void dsm_init(uint8_t npins, const uint8_t* pins) { /* Assert number of pins is correct */ if (npins > MAX_DSM_PINS) { debug("Incorrect number of DSM pins (%d)\n", npins); return; } /* Save pins information */ dsmInfo.usedPins = npins; for (uint8_t i = 0 ; i < npins; ++i) { dsmInfo.pins[i] = pins[i]; /* configure GPIOs */ gpio_enable(pins[i], GPIO_OUTPUT); } /* Set output to LOW */ dsm_stop(); /* Flag not running */ dsmInfo.running = 0; } void dsm_set_prescale(uint8_t prescale) { //TODO: Add a freq/prescale converter dsmInfo.preScale = prescale; debug("Set Prescale: %u",dsmInfo.preScale); } void dsm_set_target(uint8_t target) { dsmInfo.target = target; if (target == 0 || target == UINT8_MAX) { dsmInfo.output = (target == UINT8_MAX); } debug("Duty set at %u",dsmInfo.target); if (dsmInfo.running) { dsm_start(); } } void dsm_start() { if (dsmInfo.target > 0 && dsmInfo.target < UINT8_MAX) { for (uint8_t i = 0; i < dsmInfo.usedPins; ++i) { SET_MASK_BITS(GPIO.CONF[dsmInfo.pins[i]], GPIO_CONF_SOURCE_DSM); } GPIO.DSM = GPIO_DSM_ENABLE | (dsmInfo.preScale << 8) | dsmInfo.target; } else { for (uint8_t i = 0; i < dsmInfo.usedPins; ++i) { gpio_write(dsmInfo.pins[i], dsmInfo.output ); } } debug("start"); dsmInfo.running = 1; } void dsm_stop() { for (uint8_t i = 0; i < dsmInfo.usedPins; ++i) { CLEAR_MASK_BITS(GPIO.CONF[dsmInfo.pins[i]], GPIO_CONF_SOURCE_DSM); gpio_write(dsmInfo.pins[i], false); } debug("stop"); dsmInfo.running = 0; }