侧边栏壁纸
博主头像
塞塞哇 博主等级

开源创客

  • 累计撰写 38 篇文章
  • 累计创建 9 个标签
  • 累计收到 11 条评论

目 录CONTENT

文章目录

Linux Kernel实现GPIO模拟SPI与I2C

塞塞蛙
2024-05-22 / 0 评论 / 0 点赞 / 332 阅读 / 0 字

Linux Kernel实现GPIO模拟SPI与I2C

模拟SPI和I2C和硬件支持的还是有一些差别,速度上会有极大的限制。

但是可以很好的解决我们硬件外设不够用的情况,但是又可以使用Linux内核中的驱动来搭配使用。

1. GPIO 模拟I2C

需要先设置内核的支持

在内核源码目录下,先进行图形化界面配置 menuconfig配置 Device Drivers > I2C support

image-eztv.png

新建一个设备树文件,添加如下内容

#include <dt-bindings/pinctrl/rockchip.h>
/{
	aliases {
		i2c6 = &i2c6;
	};
	i2c6:i2c6_gpio{
		#address-cells = <1>;
		#size-cells = <1>;
		compatible = "i2c-gpio";
		pinctrl-names = "default";
		pinctrl-0 = <&i2c6_soft>;
		gpios = <&gpio4 RK_PA1 GPIO_ACTIVE_HIGH>, /* SDA */
		<&gpio4 RK_PA3 GPIO_ACTIVE_HIGH>; /* SCL */  //先SDA后SCL顺序是死的不要变
		i2c-gpio,delay-us = <5>;
		status = "disabled";
	};
};

&pinctrl {
	i2c6{
		i2c6_soft:i2c6-soft{
			rockchip,pins = <4 RK_PA1 RK_FUNC_GPIO &pcfg_pull_none>,
			<4 RK_PA3 RK_FUNC_GPIO &pcfg_pull_none>;
		};
	};
};

注意:aliases节点必须写,总线使用aliases节点中定义的顺序去初始化总线外设等。

使用方法(触摸示例):

&i2c6{
	status = "okay";
	pinctrl-names = "default";
	pinctrl-0 = <&i2c6_soft &gpio0_pc5 &gpio0_pa5>;
	clock-frequency = <100000>;

	focaltech@38{
		status = "okay";
		compatible = "focaltech,fts";
		reg = <0x38>;//I2C地址
		interrupt-parent = <&gpio0>;
		interrupts = <RK_PC5 IRQ_TYPE_LEVEL_LOW>;
		focaltech,reset-gpio = <&gpio0 RK_PA5 GPIO_ACTIVE_LOW>;
		focaltech,irq-gpio = <&gpio0 RK_PC5 GPIO_ACTIVE_HIGH>;

		focaltech,max-touch-number = <5>;//最大触摸数量-多点触摸配置
		focaltech,display-coords =  <0 0 240 320>;//分辨率
	};
};

2. GPIO模拟SPI

需要先设置内核的支持

在内核源码目录下,先进行图形化界面配置 menuconfig配置 Device Drivers > SPI support

image-yuri.png

#include <dt-bindings/pinctrl/rockchip.h>
/{
	aliases {
        spi5 = &spi5;
	};
	spi5:spi5_gpio{
		compatible = "spi-gpio";
		#address-cells = <0x1>;
		ranges;
		pinctrl-names = "default";
		pinctrl-0 = <&spi6_soft>;

		sck-gpios = <&gpio4 RK_PA0 0>;
		mosi-gpios = <&gpio3 RK_PD7 0>;

		miso-gpios = <&gpio3 RK_PA1 0>;
		cs-gpios = <&gpio3 RK_PA2 0>;
		num-chipselects = <1>;
		status = "disabled";
	};
};

&pinctrl {
	spi5{
		spi5_soft:spi5-soft{
			rockchip,pins = <3 RK_PD7 RK_FUNC_GPIO &pcfg_pull_none>,
			<4 RK_PA0 RK_FUNC_GPIO &pcfg_pull_none>;
		};
	};
};

注意:aliases节点必须写总线使用aliases节点中定义的顺序去初始化总线外设等。

使用方法(屏幕驱动示例):

&spi5{
	status = "okay";
	pinctrl-names = "default";
	pinctrl-0 = <&spi5_soft &gpio3_pd6 &gpio4_pa2 &gpio0_pc0>;
	#address-cells = <1>;
	#size-cells = <0>;
	tft: lcd@0{
		compatible = "sitronix,st7789v";
		spi-max-frequency = <100000000>;//40Mh
		// spi-max-frequency = <80000000>;
		reg = <0>;//SPI序号
		spi-cpol;
		spi-cpha;
		rotate = <90>;// 旋转角度,lcd驱动里会读取并设置对应寄存器
		fps = <30>;
		width = <240>;
		height = <320>;
	    invert;
		// bgr = <0>;
		buswidth = <8>;//SPI 8位数据长度
		led-gpios = <&gpio3 RK_PA4 GPIO_ACTIVE_LOW>;//BL
		dc-gpios = <&gpio3 RK_PA7 GPIO_ACTIVE_LOW>;//DC
		reset-gpios = <&gpio3 RK_PB5 GPIO_ACTIVE_HIGH>;//RES
		cs-gpios = <&gpio3 RK_PA5 GPIO_ACTIVE_LOW>;//CS
		// debug = <0x7>;
	};
};
0
  1. 支付宝打赏

    qrcode alipay
  2. 微信打赏

    qrcode weixin

评论区