int main(void) { /* Comparator example app * * This app sets up comparator 0 to fire an interrupt when the input * voltage is greater than the reference voltage (0.95V) * * On the Intel(R) Quark(TM) Microcontroller D2000 Development Platform * the pin used is marked "SSO 10" */ qm_ac_config_t ac_cfg; QM_PUTS("Analog Comparators example app start\n"); /* Set up pin muxing and request IRQ*/ qm_pmux_select(QM_PIN_ID_0, QM_PMUX_FN_1); qm_pmux_input_en(QM_PIN_ID_0, true); qm_irq_request(QM_IRQ_AC, qm_ac_isr); /* Write configs */ ac_cfg.reference = BIT(0); /* Ref internal voltage */ ac_cfg.polarity = 0x0; /* Fire if greater than ref (high level) */ ac_cfg.power = BIT(0); /* Normal operation mode */ ac_cfg.int_en = BIT(0); /* AIN0 enable */ ac_cfg.callback = ac_example_callback; qm_ac_set_config(&ac_cfg); QM_PUTS("Analog Comparators example app complete\n"); return 0; }
static void deep_sleep_test(void) { /* * Setup the RTC to get out of sleep mode. deep sleep will require an * analog comparator interrupt to wake up the system. */ uint32_t pmux_sel_save[2], pmux_in_en_save, pmux_pullup_save; qm_ac_config_t ac_cfg; /* * Physical step at this stage to raise the V on the comparator * pin. * * Go to deep sleep, a comparator should wake me up. */ ac_cfg.reference = BIT(WAKEUP_COMPARATOR_PIN); /* Ref internal voltage. */ ac_cfg.polarity = 0x0; /* Fire if greater than ref (high level). */ ac_cfg.power = BIT(WAKEUP_COMPARATOR_PIN); /* Normal operation mode. */ ac_cfg.int_en = BIT(WAKEUP_COMPARATOR_PIN); /* Enable comparator. */ ac_cfg.callback = ac_example_callback; qm_ac_set_config(&ac_cfg); qm_irq_request(QM_IRQ_COMPARATOR_0_INT, qm_comparator_0_isr); /* * Comparator pin will fire an interrupt when the input voltage * is greater than the reference voltage (0.95V). */ /* * In order to minimise power, pmux_sel must be set to 0, input * enable must be cleared for any pins not expecting to be * used to wake the SoC from deep sleep mode, in this example * we are using AC 6. */ pmux_sel_save[0] = QM_SCSS_PMUX->pmux_sel[0]; pmux_sel_save[1] = QM_SCSS_PMUX->pmux_sel[1]; pmux_in_en_save = QM_SCSS_PMUX->pmux_in_en[0]; pmux_pullup_save = QM_SCSS_PMUX->pmux_pullup[0]; QM_SCSS_PMUX->pmux_sel[0] = QM_SCSS_PMUX->pmux_sel[1] = 0; QM_SCSS_PMUX->pmux_in_en[0] = BIT(WAKEUP_COMPARATOR_PIN); QM_SCSS_PMUX->pmux_pullup[0] = 0; /* Mux out comparator. */ qm_pmux_select(QM_PIN_ID_6, QM_PMUX_FN_1); qm_pmux_input_en(QM_PIN_ID_6, true); ENTER_C2LP(); /* Restore previous pinmuxing settings. */ QM_SCSS_PMUX->pmux_sel[0] = pmux_sel_save[0]; QM_SCSS_PMUX->pmux_sel[1] = pmux_sel_save[1]; QM_SCSS_PMUX->pmux_in_en[0] = pmux_in_en_save; QM_SCSS_PMUX->pmux_pullup[0] = pmux_pullup_save; }
static int aio_qmsi_cmp_configure(struct device *dev, u8_t index, enum aio_cmp_polarity polarity, enum aio_cmp_ref refsel, aio_cmp_cb cb, void *param) { struct aio_qmsi_cmp_dev_data_t *dev_data = (struct aio_qmsi_cmp_dev_data_t *)dev->driver_data; if (index >= AIO_QMSI_CMP_COUNT) { return -EINVAL; } aio_qmsi_cmp_disable(dev, index); dev_data->cb[index].cb = cb; dev_data->cb[index].param = param; if (refsel == AIO_CMP_REF_A) { config.reference &= ~(1 << index); } else { config.reference |= (1 << index); } if (polarity == AIO_CMP_POL_RISE) { config.polarity &= ~(1 << index); } else { config.polarity |= (1 << index); } /* The driver will not use QMSI callback mechanism */ config.callback = NULL; /* Enable comparator */ config.cmp_en |= (1 << index); config.power |= (1 << index); if (qm_ac_set_config(&config) != 0) { return -EINVAL; } /* Enable Interrupts to current core for an specific comparator */ CMP_INTR_ROUTER &= ~(1 << index); return 0; }
static int aio_qmsi_cmp_disable(struct device *dev, u8_t index) { if (index >= AIO_QMSI_CMP_COUNT) { return -EINVAL; } /* Disable interrupt to current core */ CMP_INTR_ROUTER |= (1 << index); /* Disable comparator according to index */ config.cmp_en &= ~(1 << index); config.power &= ~(1 << index); config.reference &= ~(1 << index); config.polarity &= ~(1 << index); if (qm_ac_set_config(&config) != 0) { return -EINVAL; } return 0; }
/* Low power app example */ int main(void) { /* Setup the RTC to get out of sleep mode. deep sleep will require an */ /* analog comparator interrupt to wake up the system. */ /* Variables */ uint32_t pmux_sel_save[2], pmux_in_en_save, pmux_pullup_save; qm_ac_config_t ac_cfg; qm_rtc_config_t rtc_cfg; QM_PUTS("Low power mode example."); clk_periph_enable(CLK_PERIPH_RTC_REGISTER | CLK_PERIPH_CLK); /* Initialise RTC configuration. */ rtc_cfg.init_val = 0; rtc_cfg.alarm_en = 1; rtc_cfg.alarm_val = QM_RTC_ALARM_SECOND; rtc_cfg.callback = rtc_example_callback; qm_rtc_set_config(QM_RTC_0, &rtc_cfg); qm_irq_request(QM_IRQ_RTC_0, qm_rtc_isr_0); QM_PUTS("CPU Halt."); /* Halt the CPU, RTC alarm will wake me up. */ cpu_halt(); QM_PUTS("CPU Halt wakeup."); /* Set another alarm one minute from now. */ qm_rtc_set_alarm(QM_RTC_0, QM_RTC[QM_RTC_0].rtc_ccvr + QM_RTC_ALARM_SECOND); QM_PUTS("Go to sleep."); /* Go to sleep, RTC will wake me up. */ soc_sleep(); QM_PUTS("Wake up from sleep."); /* Physical step at this stage to raise the V on the comparator pin. */ /* Go to deep sleep, a comparator should wake me up. */ QM_PUTS("Go to deep sleep."); ac_cfg.reference = BIT(WAKEUP_COMPARATOR_PIN); /* Ref internal voltage */ ac_cfg.polarity = 0x0; /* Fire if greater than ref (high level) */ ac_cfg.power = BIT(WAKEUP_COMPARATOR_PIN); /* Normal operation mode */ ac_cfg.int_en = BIT(WAKEUP_COMPARATOR_PIN); /* Enable comparator */ ac_cfg.callback = ac_example_callback; qm_ac_set_config(&ac_cfg); qm_irq_request(QM_IRQ_AC, qm_ac_isr); /* * Comparator pin will fire an interrupt when the input voltage is * greater than the reference voltage (0.95V). */ /* * In order to minimise power, pmux_sel must be set to 0, input enable * must be cleared for any pins not expecting to be used to wake the * SoC from deep sleep mode, in this example we are using AC 6. */ pmux_sel_save[0] = QM_SCSS_PMUX->pmux_sel[0]; pmux_sel_save[1] = QM_SCSS_PMUX->pmux_sel[1]; pmux_in_en_save = QM_SCSS_PMUX->pmux_in_en[0]; pmux_pullup_save = QM_SCSS_PMUX->pmux_pullup[0]; QM_SCSS_PMUX->pmux_sel[0] = QM_SCSS_PMUX->pmux_sel[1] = 0; QM_SCSS_PMUX->pmux_in_en[0] = BIT(WAKEUP_COMPARATOR_PIN); QM_SCSS_PMUX->pmux_pullup[0] = 0; /* Mux out comparator */ qm_pmux_select(QM_PIN_ID_6, QM_PMUX_FN_1); qm_pmux_input_en(QM_PIN_ID_6, true); soc_deep_sleep(); /* Restore previous pinmuxing settings. */ QM_SCSS_PMUX->pmux_sel[0] = pmux_sel_save[0]; QM_SCSS_PMUX->pmux_sel[1] = pmux_sel_save[1]; QM_SCSS_PMUX->pmux_in_en[0] = pmux_in_en_save; QM_SCSS_PMUX->pmux_pullup[0] = pmux_pullup_save; QM_PUTS("Wake up from deep sleep."); return 0; }