spi驱动st7796代码
时间: 2023-05-16 11:02:20 浏览: 942
ST7796是一款LCD控制器,其使用时需要通过SPI来与主机进行通信。所以,编写SPI驱动程序就成了使用该控制器的必要步骤。
以下是一份可供参考的ST7796的SPI驱动代码:
```c
#include <linux/spi/spi.h>
#include <linux/module.h>
/*定义SPI设备信息*/
#define SPI_BUS_NUM 2
static struct spi_device *st7796_spi_device;
/*SPI传输信息*/
static struct spi_transfer st7796_spi_transfers[2];
static unsigned char st7796_frame_control = 0;
static unsigned char st7796_display_mode = 0;
/* 将SPI传输结果输出到屏幕上 */
static void st7796_show_result(unsigned char *buf, int len)
{
int i;
for (i = 0; i < len; i++) {
printk(KERN_CRIT "%02X ", buf[i]);
}
printk(KERN_CRIT "\n");
}
/* 初始化SPI设备 */
static int st7796_spi_probe(struct spi_device *spi)
{
st7796_spi_device = spi;
return 0;
}
/* 取消SPI设备的使用 */
static int st7796_spi_remove(struct spi_device *spi)
{
st7796_spi_device = NULL;
return 0;
}
/* SPI传输完成后的回调函数 */
static void st7796_spi_complete(void *ref)
{
st7796_show_result((unsigned char *)ref, st7796_spi_transfers[1].len);
}
/*写出SPI传输信息*/
static void st7796_spi_write(const unsigned char *data, int len)
{
struct spi_message msg;
spi_message_init(&msg);
/* 实现 SPI 数据传输的 API */
st7796_spi_transfers[0].tx_buf = (void *) data;
st7796_spi_transfers[0].len = len;
st7796_spi_transfers[1].rx_buf = (void *)&st7796_frame_control;
st7796_spi_transfers[1].len = sizeof(st7796_frame_control);
st7796_spi_transfers[1].delay_usecs = 10;
spi_message_add_tail(&st7796_spi_transfers[0], &msg);
spi_message_add_tail(&st7796_spi_transfers[1], &msg);
spi_message_set_completion(&msg, st7796_spi_complete, (void *)data);
/* 将消息同步发送到 SPI 控制器 */
spi_sync(st7796_spi_device, &msg);
}
/*配置SPI参数*/
static int st7796_spi_setup(void)
{
int ret;
struct spi_master *master;
struct spi_device *spi;
/*获取SPI总线信息*/
master = spi_busnum_to_master(SPI_BUS_NUM);
if (!master) {
printk(KERN_CRIT "spi master not found");
return -ENODEV;
}
/*定义SPI设备*/
spi = spi_alloc_device(master);
if (!spi) {
printk(KERN_CRIT "can not alloate spi device");
return -ENOMEM;
}
/*初始化 SPI 设备对应的结构体*/
spi->bits_per_word = 8;
spi->max_speed_hz = 2 * 1000 * 1000;
spi->mode = SPI_MODE_0;
spi->chip_select = 0;
spi->controller_data = &st7796_spi_device;
/*配置 SPI 传输和回调函数*/
spi->setup = st7796_spi_setup;
spi->probe = st7796_spi_probe;
spi->remove = st7796_spi_remove;
/*将 spi_device 确定为所属的 spi_master 的一员*/
ret = spi_add_device(spi);
if (ret < 0) {
printk(KERN_CRIT "can not add spi device");
return ret;
}
st7796_spi_device = spi;
return 0;
}
/* 清除屏幕上的画面 */
static void st7796_clear_screen(void)
{
unsigned char data = 0x01;
st7796_spi_write(&data, sizeof(data)); /* 发送清屏指令 */
}
/*配置显示模式*/
static void st7796_display_config(void)
{
st7796_frame_control = 0x06;
st7796_display_mode = 0x2C;
/*先发送数据模式,再发送帧控制模式*/
st7796_spi_write(&st7796_display_mode, sizeof(st7796_display_mode));
st7796_spi_write(&st7796_frame_control, sizeof(st7796_frame_control));
}
static int __init st7796_init(void)
{
int ret;
ret = st7796_spi_setup(); /* 初始化SPI设备 */
if (ret < 0) {
printk(KERN_CRIT "setup spi error\n");
return -ENODEV;
}
st7796_clear_screen(); /* 清屏 */
st7796_display_config(); /* 配置显示模式 */
return 0;
}
static void __exit st7796_exit(void)
{
spi_unregister_device(st7796_spi_device);
}
MODULE_LICENSE("GPL");
MODULE_AUTHOR("xxx");
MODULE_DESCRIPTION("ST7796 SPI Driver");
MODULE_VERSION("1.0");
module_init(st7796_init);
module_exit(st7796_exit);
```
这份代码主要实现了SPI的驱动程序,通过定义SPI总线设备进行通信。在初始化之后,可以通过向ST7796发送指令来控制其显示画面。此外,还可以利用回调函数来处理SPI传输之后的响应信息。
值得指出的是,这份代码只是一个简单的示例,还需要根据具体的项目进行修改才能正常使用。用户可以依据此代码进行参考,以实现自己的SPI驱动程序。
阅读全文