[IMX6ULL ドライバーの開発と学習] 22. IMX6ULL 開発ボードは ADC を読み取ります (MQ-135 を例にします)

IMX6ULL には 2 つの ADC があり、各 ADC には 8 チャンネルがありますが、ADC コントローラーを共有します。

ここに画像の説明を挿入

1. デバイスツリー

imx6ull.dtsi ファイルには、adc1 のノード部分情報が定義されています。

adc1: adc@02198000 {
    
    
	compatible = "fsl,imx6ul-adc", "fsl,vf610-adc";
	reg = <0x02198000 0x4000>;
	interrupts = <GIC_SPI 100 IRQ_TYPE_LEVEL_HIGH>;
	clocks = <&clks IMX6UL_CLK_ADC1>;
	num-channels = <2>;
	clock-names = "adc";
	status = "disabled";
};

num-channels = <2>;であることに注意してください。これは、ADC1 の 2 つのチャネル、つまりチャネル 1 とチャネル 2 の使用を指定することを意味します。
複数の ADC チャネルを使用したい場合は、この値を変更するだけです。

ADC ピンのpinctrlを設定し、独自のデバイス ツリー (.dts) で adc1 を参照し、pinctrl サブシステムを指定します。つまり、ピンを指定します。

まず、ルートノードの下にpinctrlを定義します。

/* chenshao ADC1_CH1 GPIO1_IO01 */
pinctrl_adc1: adc1grp {
    
    
	fsl,pins = <
		MX6UL_PAD_GPIO1_IO01__GPIO1_IO01   0xb0 
	>;
};

次に、レギュレータ ノードの下の ADC の基準電圧を 5V に設定します (MQ135 が出力する最大アナログ電圧は5Vであるため)。

/* chenshao ADC vref 5.0V */
reg_vref_adc: regulator@2 {
    
    
	compatible = "regulator-fixed";
	regulator-name = "VREF_5V";
	regulator-min-microvolt = <5000000>;
	regulator-max-microvolt = <5000000>;
};

最後に、ルート ノードの外側にある adc1 ノードを参照し、ピンが電圧ノードを参照できることを指定します。

/* chenshao ADC1 */
&adc1 {
    
    
	pinctrl-names = "default";
	pinctrl-0 = <&pinctrl_adc1>;
	num-channels = <2>;             /* 2个通道,gpio1_io0占用一个 */
	vref-supply = <&reg_vref_adc>;
	status = "okay";	
};

2. ADC 値を直接確認する

1.进入iio总线下的设备目录
cd /sys/bus/iio/devices/iio:device0/

2.ls查看
------------------------
dev                            of_node
in_voltage0_raw                power
in_voltage1_raw                sampling_frequency_available
in_voltage_sampling_frequency  subsystem
in_voltage_scale               uevent
name

3.查看ADC通道1原始值(由于IMX6ULL ADC为12位,所以最小值为0,最大值为40952^12),分别对应0V,3.3V或5V)
cat in_voltage1_raw 
721


4.查看电压规模
cat in_voltage_scale 
1.220703125

5.计算实际电压
in_voltage1_raw  * in_voltage_scale 即可,注意单位是毫伏

3. アプリケーションは ADC と電圧を取得します

/sys/bus/iio/devices/iio:device0/in_voltage1_rawファイルを読み取り、ADC の生の値を取得します。 /sys/bus/iio/devices/iio:device0/in_voltage_scale
ファイルを読み取り、電力スケール値を取得します。2 つと1000で割って電圧値(V単位)を取得します。

PS:ファイルを読み取る前に巻き戻し関数を
使用してカーソルを先頭に移動します。fscanf を使用してファイルを読み取り、atoi および atof ライブラリ関数を使用して型を変換できます。

#include <stdio.h>
#include <stdlib.h>
#include <string.h>

#include <unistd.h>


const char *voltage1_raw = "/sys/bus/iio/devices/iio:device0/in_voltage1_raw";
const char *voltage_scale = "/sys/bus/iio/devices/iio:device0/in_voltage_scale";

int main(int argc, char *argv[])
{
    
    
	FILE *raw_fd, *scale_fd;
	int len1, len2, res;
	char data[20];
	int raw;
	double scale;

	while(1){
    
    
		/* 1.打开文件 */
		raw_fd = fopen(voltage1_raw, "r");
		if(raw_fd == NULL){
    
    
			printf("open raw_fd failed!\n");
			return -1;
		}

		scale_fd = fopen(voltage_scale, "r");
		if(scale_fd == NULL){
    
    
			printf("open scale_fd failed!\n");
			return -2;
		}
	
		/* 2.读取文件 */
		rewind(raw_fd);   // 将光标移回文件开头
		res = fscanf(raw_fd, "%s", data);
		raw = atoi(data);

		memset(data, 0, sizeof(data));
		rewind(scale_fd);   // 将光标移回文件开头
		res = fscanf(scale_fd, "%s", data);
		scale = atof(data);
		

		printf("ADC原始值:%d,电压值:%.3fV\r\n", raw, raw * scale / 1000.f);

		fclose(raw_fd);
		fclose(scale_fd);
		sleep(2);
	}

	return 0;
}

テストの成功

# ./adcApp
ADC原始值:390,电压值:0.476V
ADC原始值:399,电压值:0.487V
ADC原始值:413,电压值:0.504V
ADC原始值:416,电压值:0.508V
ADC原始值:410,电压值:0.500V
ADC原始值:407,电压值:0.497V

おすすめ

転載: blog.csdn.net/HuangChen666/article/details/132056736