|
@@ -0,0 +1,104 @@
|
|
|
+#include "hardware/adc.h"
|
|
|
+#include "hardware/irq.h"
|
|
|
+#include "pico/multicore.h"
|
|
|
+#include "hardware/clocks.h"
|
|
|
+
|
|
|
+#include "adrs2040U_i2c.h"
|
|
|
+
|
|
|
+#define ADC_BUFF_SIZE 0x100
|
|
|
+
|
|
|
+auto_init_mutex(adcbuff_mutex);
|
|
|
+
|
|
|
+static volatile int read_p;
|
|
|
+static volatile int write_p;
|
|
|
+static volatile uint16_t adc_buffer[ADC_BUFF_SIZE];
|
|
|
+
|
|
|
+static void adc_interrupt(void)
|
|
|
+{
|
|
|
+ while(! adc_fifo_is_empty()) {
|
|
|
+ mutex_enter_blocking(&adcbuff_mutex);
|
|
|
+ adc_buffer[write_p] = adc_fifo_get() & 0xFFF;
|
|
|
+ write_p = (write_p + 1) & (ADC_BUFF_SIZE - 1);
|
|
|
+ mutex_exit(&adcbuff_mutex);
|
|
|
+ }
|
|
|
+};
|
|
|
+
|
|
|
+class ADC_Driver {
|
|
|
+ private:
|
|
|
+
|
|
|
+ int sample_rate = 1000;
|
|
|
+ uint32_t adc_clk;
|
|
|
+
|
|
|
+ uint8_t adc_pin;
|
|
|
+ uint8_t adc_channel;
|
|
|
+
|
|
|
+ public:
|
|
|
+ ADC_Driver(uint8_t p = 26, uint8_t c = 0) : adc_pin(p), adc_channel(c)
|
|
|
+ {
|
|
|
+ read_p = write_p = 0;
|
|
|
+ sample_rate = 1000;
|
|
|
+ adc_init();
|
|
|
+ adc_gpio_init(adc_pin);
|
|
|
+ adc_select_input(adc_channel);
|
|
|
+ adc_fifo_setup(true, false, 1, true, false);
|
|
|
+ // ADCサンプリングクロック設定
|
|
|
+ adc_clk = clock_get_hz(clk_adc);
|
|
|
+ adc_set_clkdiv(adc_clk/sample_rate);
|
|
|
+ // ADC割り込み
|
|
|
+ irq_set_exclusive_handler(ADC_IRQ_FIFO, adc_interrupt);
|
|
|
+ irq_set_enabled(ADC_IRQ_FIFO, true);
|
|
|
+ run(false);
|
|
|
+ };
|
|
|
+
|
|
|
+
|
|
|
+ int get_sample_rate(void)
|
|
|
+ {
|
|
|
+ return sample_rate;
|
|
|
+ };
|
|
|
+
|
|
|
+ void set_sample_rate(int rate)
|
|
|
+ {
|
|
|
+ sample_rate = rate;
|
|
|
+ adc_set_clkdiv(adc_clk/sample_rate);
|
|
|
+ };
|
|
|
+
|
|
|
+ bool is_empty(void)
|
|
|
+ {
|
|
|
+ return (read_p == write_p);
|
|
|
+ };
|
|
|
+
|
|
|
+ int get_value(void)
|
|
|
+ {
|
|
|
+ int wp;
|
|
|
+ int rv;
|
|
|
+
|
|
|
+ mutex_enter_blocking(&adcbuff_mutex);
|
|
|
+ wp = write_p;
|
|
|
+ mutex_exit(&adcbuff_mutex);
|
|
|
+ if(read_p != wp) {
|
|
|
+ rv = adc_buffer[read_p];
|
|
|
+ read_p = (read_p + 1) & (ADC_BUFF_SIZE - 1);
|
|
|
+ }
|
|
|
+ else
|
|
|
+ rv = -1;
|
|
|
+
|
|
|
+ return rv;
|
|
|
+ };
|
|
|
+
|
|
|
+ uint8_t count(void)
|
|
|
+ {
|
|
|
+ uint8_t r;
|
|
|
+ mutex_enter_blocking(&adcbuff_mutex);
|
|
|
+ r = write_p - read_p;
|
|
|
+ mutex_exit(&adcbuff_mutex);
|
|
|
+
|
|
|
+ return r;
|
|
|
+ }
|
|
|
+
|
|
|
+ void run(bool r)
|
|
|
+ {
|
|
|
+ adc_irq_set_enabled(r);
|
|
|
+ adc_run(r);
|
|
|
+ };
|
|
|
+
|
|
|
+};
|