Ejemplo n.º 1
0
static int adc_qmsi_read(struct device *dev, struct adc_seq_table *seq_tbl)
{
	int i, ret = 0;
	qm_adc_xfer_t xfer;
	qm_adc_config_t cfg;

	struct adc_info *info = dev->driver_data;

	if (qm_adc_get_config(QM_ADC_0, &cfg) != QM_RC_OK) {
		return -ENOTSUP;
	}

	for (i = 0; i < seq_tbl->num_entries; i++) {

		xfer.ch = (qm_adc_channel_t *)&seq_tbl->entries[i].channel_id;
		/* Just one channel at the time using the Zephyr sequence table */
		xfer.ch_len = 1;
		xfer.samples = (uint32_t *)seq_tbl->entries[i].buffer;

		/* buffer length (bytes) the number of samples, the QMSI Driver does
		 * not allow more than QM_ADC_FIFO_LEN samples at the time in polling
		 * mode, if that happens, the qm_adc_convert api will return with an
		 * error
		 */
		xfer.samples_len = (seq_tbl->entries[i].buffer_length);
		xfer.complete_callback = NULL;
		xfer.error_callback = NULL;

		cfg.window = seq_tbl->entries[i].sampling_delay;

		adc_lock(info);

		if (qm_adc_set_config(QM_ADC_0, &cfg) != QM_RC_OK) {
			ret =  -EINVAL;
			adc_unlock(info);
			break;
		}

		/* Run the conversion, here the function will poll for the samples
		 * The function will constantly read  the status register to check if
		 * the number of samples required has been captured
		 */
		if (qm_adc_convert(QM_ADC_0, &xfer) != QM_RC_OK) {
			ret =  -EIO;
			adc_unlock(info);
			break;
		}

		/* Successful Analog to Digital conversion */
		adc_unlock(info);
	}

	return ret;
}
Ejemplo n.º 2
0
static void adc_qmsi_enable(struct device *dev)
{
	struct adc_info *info = dev->driver_data;

	adc_lock(info);
	qm_adc_set_mode(QM_ADC_0, QM_ADC_MODE_NORM_NO_CAL);
	adc_unlock(info);
}
Ejemplo n.º 3
0
static void adc_qmsi_disable(struct device *dev)
{
	struct adc_info *info = dev->driver_data;

	adc_lock(info);
	/* Go to deep sleep */
	qm_adc_set_mode(QM_ADC_0, QM_ADC_MODE_DEEP_PWR_DOWN);
	adc_unlock(info);
}
Ejemplo n.º 4
0
ADC_GET(nxp, adc, waittime) {
	/* Lock ADC */
	adc_lock(adc, waittime, -1);
	/* Lock ADC Controller */
	CTRL_LOCK(adc, waittime, -1);
	/* TODO implement */
	CTRL_UNLOCK(adc, -1);
	adc_unlock(adc, -1);
	return -1;
}
Ejemplo n.º 5
0
static int adc_qmsi_read(struct device *dev, struct adc_seq_table *seq_tbl)
{
	int i, ret = 0;
	qm_adc_xfer_t xfer;
	qm_adc_config_t cfg;

	struct adc_info *info = dev->driver_data;

	if (qm_adc_get_config(QM_ADC_0, &cfg) != QM_RC_OK) {
		return -ENOTSUP;
	}

	for (i = 0; i < seq_tbl->num_entries; i++) {

		xfer.ch = (qm_adc_channel_t *)&seq_tbl->entries[i].channel_id;
		/* Just one channel at the time using the Zephyr sequence table */
		xfer.ch_len = 1;
		xfer.samples = (uint32_t *)seq_tbl->entries[i].buffer;
		xfer.samples_len = (seq_tbl->entries[i].buffer_length) >> 2;
		xfer.complete_callback = complete_callback;
		xfer.error_callback = error_callback;

		cfg.window = seq_tbl->entries[i].sampling_delay;

		adc_lock(info);

		if (qm_adc_set_config(QM_ADC_0, &cfg) != QM_RC_OK) {
			ret =  -EINVAL;
			adc_unlock(info);
			break;
		}

		/* ADC info used by the callbacks */
		adc_context = info;

		/* This is the interrupt driven API, will generate and interrupt and
		 * call the complete_callback function once the samples have been
		 * obtained
		 */
		if (qm_adc_irq_convert(QM_ADC_0, &xfer) != QM_RC_OK) {
			adc_context = NULL;
			ret =  -EIO;
			adc_unlock(info);
			break;
		}

		/* Wait for the interrupt to finish */
		device_sync_call_wait(&info->sync);

		if (info->state == ADC_STATE_ERROR) {
			ret =  -EIO;
			adc_unlock(info);
			break;
		}
		adc_context = NULL;

		/* Successful Analog to Digital conversion */
		adc_unlock(info);
	}

	return ret;
}