日期:2014-05-16 浏览次数:20743 次
一.spi设备
struct spi_device { struct device dev; //设备文件 struct spi_master *master; //spi主机 u32 max_speed_hz; //最大速率 u8 chip_select; //片选 u8 mode; //模式 u8 bits_per_word; //一个字有多少位 int irq; //中断号 void *controller_state; //控制器状态 void *controller_data; //控制器数据 char modalias[SPI_NAME_SIZE];//名字 };
2.spi传输模式:
#define SPI_CPHA 0x01 //时钟相位 #define SPI_CPOL 0x02 //时钟继续 #define SPI_MODE_0 (0|0) //模式0 #define SPI_MODE_1 (0|SPI_CPHA) //模式1 #define SPI_MODE_2 (SPI_CPOL|0) //模式2 #define SPI_MODE_3 (SPI_CPOL|SPI_CPHA) //模式3 #define SPI_CS_HIGH 0x04 //片选高电平 #define SPI_LSB_FIRST 0x08 //LSB #define SPI_3WIRE 0x10 //3线模式 SI和SO同一根线 #define SPI_LOOP 0x20 //回送模式 #define SPI_NO_CS 0x40 //单个设备占用一根SPI总线,所以没片选 #define SPI_READY 0x80 //从机拉低电平停止数据传输
3.spi设备的添加spi_new_device
struct spi_device *spi_new_device(struct spi_master *master,struct spi_board_info *chip) { struct spi_device *proxy; int status; proxy = spi_alloc_device(master); //3.1 spi设备初始化 if (!proxy) return NULL; WARN_ON(strlen(chip->modalias) >= sizeof(proxy->modalias)); proxy->chip_select = chip->chip_select; //片选 proxy->max_speed_hz = chip->max_speed_hz; //最大速率 proxy->mode = chip->mode; //模式 proxy->irq = chip->irq; //中断号 strlcpy(proxy->modalias, chip->modalias, sizeof(proxy->modalias)); proxy->dev.platform_data = (void *) chip->platform_data; proxy->controller_data = chip->controller_data; proxy->controller_state = NULL; status = spi_add_device(proxy); //3.2 添加spi设备 if (status < 0) { spi_dev_put(proxy); //增加spi设备引用计数 return NULL; } return proxy; } EXPORT_SYMBOL_GPL(spi_new_device);
3.1.分配spi设备
struct spi_device *spi_alloc_device(struct spi_master *master) { struct spi_device *spi; struct device *dev = master->dev.parent; if (!spi_master_get(master)) //判断spi主机是否存在 return NULL; spi = kzalloc(sizeof *spi, GFP_KERNEL); //分配内存 if (!spi) { dev_err(dev, "cannot alloc spi_device\n"); spi_master_put(master); //增加主机引用计数 return NULL; } spi->master = master; //设置spi主机 spi->dev.parent = dev; //spi设备文件的父设备为spi主机设备文件的父设备 spi->dev.bus = &spi_bus_type; //总线类型 spi->dev.release = spidev_release; //释放方法 device_initialize(&spi->dev); //设备初始化 return spi; } EXPORT_SYMBOL_GPL(spi_alloc_device);
3.2 添加spi设备
int spi_add_device(struct spi_device *spi) { static DEFINE_MUTEX(spi_add_lock); struct device *dev = spi->master->dev.parent; struct device *d; int status; if (spi->chip_select >= spi->master->num_chipselect) { dev_err(dev, "cs%d >= max %d\n",spi->chip_select,spi->master->num_chipselect); return -EINVAL; } dev_set_name(&spi->dev, "%s.%u", dev_name(&spi->master->dev),spi->chip_select); mutex_lock(&spi_add_lock); d = bus_find_device_by_name(&spi_bus_type, NULL, dev_name(&spi->dev)); //查找总线上的spi设备 if (d != NULL) { //判断是否已经在使用了 dev_err(dev, "chipselect %d already in use\n",spi->chip_select); put_device(d); status = -EBUSY; goto done; } status = spi_setup(spi); //调用spi主机 setup方法 if (status < 0) { dev_err(dev, "can't setup %s, status %d\n",dev_name(&spi->dev), status); goto done; } status = device_add(&spi->dev); //添加设备 if (status < 0) dev_err(dev, "can't add %s, status %d\n",dev_name(&spi->dev), status); else dev_dbg(dev, "registered child %s\n", dev_name(&spi->dev)); done: mutex_unlock(&spi_add_lock); return status; } EXPORT_SYMBOL_GPL(spi_add_device);
3.2.1 spi setup方法
int spi_setup(struct spi_device *spi) { unsigned bad_bits; int status; ba