先给出Linux SPI子系统的体系结构图:

SPI子系统体系结构

下面开始分析SPI子系统。

Linux中SPI子系统的初始化是从drivers/spi/spi.c文件中的spi_init函数开始的,看看它的定义:

00001025 static int __init spi_init(void)
00001026 {
00001027     int    status;
00001028
00001029     buf = kmalloc(SPI_BUFSIZ, GFP_KERNEL);
00001030     if (!buf) {
00001031         status = -ENOMEM;
00001032         goto err0;
00001033     }
00001034
00001035     status = bus_register(&spi_bus_type);
00001036     if (status < 0)
00001037         goto err1;
00001038
00001039     status = class_register(&spi_master_class);
00001040     if (status < 0)
00001041         goto err2;
00001042     return 0;
00001043
00001044 err2:
00001045     bus_unregister(&spi_bus_type);
00001046 err1:
00001047     kfree(buf);
00001048     buf = NULL;
00001049 err0:
00001050     return status;
00001051 }

1029行,分配spi buf内存,其中buf和SPI_BUFSIZ都在spi.c文件中定义:

00000945 #define    SPI_BUFSIZ    max(32,SMP_CACHE_BYTES)
00000946
00000947 static u8    *buf;

1035行,注册spi总线,同样是在spi.c文件中:

00000145 struct bus_type spi_bus_type = {
00000146     .name        = "spi",
00000147     .dev_attrs    = spi_dev_attrs,
00000148     .match        = spi_match_device,
00000149     .uevent        = spi_uevent,
00000150     .suspend        = spi_suspend,
00000151     .resume        = spi_resume,
00000152 };

146行,总线的名字就叫spi。

148行,比较重要的,spi_match_device是spi总线上匹配设备和设备驱动的函数,同样是在spi.c文件中:

00000085 static int spi_match_device(struct device *dev, struct device_driver *drv)
00000086 {
00000087     const struct spi_device    *spi = to_spi_device(dev);
00000088     const struct spi_driver    *sdrv = to_spi_driver(drv);
00000089
00000090     /* Attempt an OF style match */
00000091     if (of_driver_match_device(dev, drv))
00000092         return 1;
00000093
00000094     if (sdrv->id_table)
00000095         return !!spi_match_id(sdrv->id_table, spi);
00000096
00000097     return strcmp(spi->modalias, drv->name) == 0;
00000098 }

写过驱动的都应该知道platform总线有struct platform_device和struct platform_driver,到了SPI总线,当然也有对应的struct spi_device和struct spi_driver,如87、88行所示。87行,关于struct spi_device的定义是在include/linux/spi/spi.h中:

00000069 struct spi_device {
00000070     struct device        dev;
00000071     struct spi_master    *master;
00000072     u32            max_speed_hz;
00000073     u8            chip_select;
00000074     u8            mode;
00000075 #define    SPI_CPHA    0x01            /* clock phase */
00000076 #define    SPI_CPOL    0x02            /* clock polarity */
00000077 #define    SPI_MODE_0    (0|0)            /* (original MicroWire) */
00000078 #define    SPI_MODE_1    (0|SPI_CPHA)
00000079 #define    SPI_MODE_2    (SPI_CPOL|0)
00000080 #define    SPI_MODE_3    (SPI_CPOL|SPI_CPHA)
00000081 #define    SPI_CS_HIGH    0x04            /* chipselect active high? */
00000082 #define    SPI_LSB_FIRST    0x08            /* per-word bits-on-wire */
00000083 #define    SPI_3WIRE    0x10            /* SI/SO signals shared */
00000084 #define    SPI_LOOP    0x20            /* loopback mode */
00000085 #define    SPI_NO_CS    0x40            /* 1 dev/bus, no chipselect */
00000086 #define    SPI_READY    0x80            /* slave pulls low to pause */
00000087     u8            bits_per_word;
00000088     int            irq;
00000089     void            *controller_state;
00000090     void            *controller_data;
00000091     char            modalias[SPI_NAME_SIZE];
00000092
00000093     /*
00000094      * likely need more hooks for more protocol options affecting how
00000095      * the controller talks to each chip, like:
00000096      *  - memory packing (12 bit samples into low bits, others zeroed)
00000097      *  - priority
00000098      *  - drop chipselect after each word
00000099      *  - chipselect delays
00000100      *  - ...
00000101      */
00000102 };

70行,dev,嵌入到设备模型中用的。

71行,master,spi设备的更高层描述,每一个spi控制器就对应一个master,一个spi设备必须对应一个master,master下可以有多个spi设备。

72,73行没什么好说的,从变量的名字就可以明白。

74行,mode,针对时钟相位CPHA(0或1)和时钟极性CPOL(0或1)的不同组合,将spi分成四种模式,就是77至80行这四种。CPOL表示当空闲时(没有进行数据传输)时钟信号的电平,CPOL=0表示低电平,CPOL=1表示高电平。每个时钟周期都有两次电平的跳变,上升沿和下降沿,CPHA就表示在每个时钟周期里是第一个边沿采样数据还是第二个边沿采样数据,具体第一个边沿或者第二个边沿是上升沿还是下降沿则由CPOL决定。看下面这张图就明白了。蓝色箭头表示对数据进行采样。

87行,如果传输是以字节为单位的话就设置为8,相应地,如果是以2个字节为单位则设置为16。

88行,中断号。89行,没有使用,在后面会看到这个值会被设置为NULL。90行,后面讲到具体的控制器再说。91行,很重要,一般来说设备与驱动能否匹配起来就要看它,注意,这里只是说一般,因为还有另外两种匹配的方法,不过大部分设备和驱动能否匹配起来都是根据名字是否相等,当然像USB驱动就不是根据名字来匹配的,而是根据与id table。struct spi_driver的定义也是在include/linux/spi/spi.h:

00000175 struct spi_driver {
00000176     const struct spi_device_id *id_table;
00000177     int            (*probe)(struct spi_device *spi);
00000178     int            (*remove)(struct spi_device *spi);
00000179     void            (*shutdown)(struct spi_device *spi);
00000180     int            (*suspend)(struct spi_device *spi, pm_message_t mesg);
00000181     int            (*resume)(struct spi_device *spi);
00000182     struct device_driver    driver;
00000183 };

182行,driver就是在设备模型中使用的那个device_driver,其他都是一些函数指针的定义,挺熟悉的了,就不多说了。

回到spi_match_device函数,91行和95行就是设备和驱动匹配的另外两种方法,因为后文要讲的spi驱动使用的是第三种方法,因此这里就不讨论这两种方法了。97行,根据设备名和驱动名是否相等进行匹配,相等则返回1,表示匹配成功,此时驱动里的probe函数将会被调用,这也是我们最希望看到的,返回0则表示匹配失败。

我们知道,对于具体的平台,nand、iic、frame buffer等这些都是平台设备,spi当然也一样是平台设备,对于平台设备,大部分情况下是先注册设备再注册驱动。因此下面就以exynos4412为具体平台,按照这种先后顺序来讲述。

exynos4412有三个SPI控制器,以SPI0为例就可以了。首先看exynos4412中关于SPI0控制器的描述,在arch/arm/mach-exynos/dev-spi.c文件中:

struct platform_device exynos_device_spi0 = {.name        = "s3c64xx-spi",.id          = 0,.num_resources     = ARRAY_SIZE(exynos_spi0_resource),.resource   = exynos_spi0_resource,.dev = {.dma_mask        = &spi_dmamask,.coherent_dma_mask  = DMA_BIT_MASK(32),.platform_data = &exynos_spi0_pdata,},
};

第2行,驱动能否与这个设备匹配,就看这个名字了,因此对应的驱动名字必须与之一样。3行,SPI控制器的ID,SPI0控制器就为0,SPI1控制器就为1。

4和5行是关于IO口资源、DMA资源和中断资源的。7、8行是关于DMA的,不说了。9行,给驱动用的,在驱动那里再说。在板初始化函数smdk4x12_machine_init里调用platform_add_devices函数就可以将SPI0设备注册到platform总线上。

exynos4412的SPI控制器驱动在drivers/spi/spi_s3c64xx.c文件里(虽然我们是exynos4412平台,但是上面exynos_device_spi0中name为"s3c64xx-spi",所以,我猜这应该是使用的s3c6410原来的驱动程序)。初始化函数:

00001183 static int __init s3c64xx_spi_init(void)
00001184 {
00001185     return platform_driver_probe(&s3c64xx_spi_driver, s3c64xx_spi_probe);
00001186 }

1185行,s3c64xx_spi_driver是struct platform_driver的实例,也在spi_s3c64xx.c文件中定义:

00001172 static struct platform_driver s3c64xx_spi_driver = {
00001173     .driver = {
00001174         .name    = "s3c64xx-spi",
00001175         .owner = THIS_MODULE,
00001176     },
00001177     .remove = s3c64xx_spi_remove,
00001178     .suspend = s3c64xx_spi_suspend,
00001179     .resume = s3c64xx_spi_resume,
00001180 };

1174行,看到了没?和之前在exynos_device_spi0里定义的名字是一样的,这样它们就可以匹配起来,1185行的s3c64xx_spi_probe驱动探测函数就会被调用,看下它的定义:

00000911 static int __init s3c64xx_spi_probe(struct platform_device *pdev)
00000912 {
00000913     struct resource    *mem_res, *dmatx_res, *dmarx_res;
00000914     struct s3c64xx_spi_driver_data *sdd;
00000915     struct s3c64xx_spi_info *sci;
00000916     struct spi_master *master;
00000917     int ret;
00000918
00000919     if (pdev->id < 0) {
00000920         dev_err(&pdev->dev,
00000921                 "Invalid platform device id-%d\n", pdev->id);
00000922         return -ENODEV;
00000923     }
00000924
00000925     if (pdev->dev.platform_data == NULL) {
00000926         dev_err(&pdev->dev, "platform_data missing!\n");
00000927         return -ENODEV;
00000928     }
00000929
00000930     sci = pdev->dev.platform_data;
00000931     if (!sci->src_clk_name) {
00000932         dev_err(&pdev->dev,
00000933             "Board init must call s3c64xx_spi_set_info()\n");
00000934         return -EINVAL;
00000935     }
00000936
00000937     /* Check for availability of necessary resource */
00000938
00000939     dmatx_res = platform_get_resource(pdev, IORESOURCE_DMA, 0);
00000940     if (dmatx_res == NULL) {
00000941         dev_err(&pdev->dev, "Unable to get SPI-Tx dma resource\n");
00000942         return -ENXIO;
00000943     }
00000944
00000945     dmarx_res = platform_get_resource(pdev, IORESOURCE_DMA, 1);
00000946     if (dmarx_res == NULL) {
00000947         dev_err(&pdev->dev, "Unable to get SPI-Rx dma resource\n");
00000948         return -ENXIO;
00000949     }
00000950
00000951     mem_res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
00000952     if (mem_res == NULL) {
00000953         dev_err(&pdev->dev, "Unable to get SPI MEM resource\n");
00000954         return -ENXIO;
00000955     }
00000956
00000957     master = spi_alloc_master(&pdev->dev,
00000958                 sizeof(struct s3c64xx_spi_driver_data));
00000959     if (master == NULL) {
00000960         dev_err(&pdev->dev, "Unable to allocate SPI Master\n");
00000961         return -ENOMEM;
00000962     }
00000963
00000964     platform_set_drvdata(pdev, master);
00000965
00000966     sdd = spi_master_get_devdata(master);
00000967     sdd->master = master;
00000968     sdd->cntrlr_info = sci;
00000969     sdd->pdev = pdev;
00000970     sdd->sfr_start = mem_res->start;
00000971     sdd->tx_dmach = dmatx_res->start;
00000972     sdd->rx_dmach = dmarx_res->start;
00000973
00000974     sdd->cur_bpw = 8;
00000975
00000976     master->bus_num = pdev->id;
00000977     master->setup = s3c64xx_spi_setup;
00000978     master->transfer = s3c64xx_spi_transfer;
00000979     master->num_chipselect = sci->num_cs;
00000980     master->dma_alignment = 8;
00000981     /* the spi->mode bits understood by this driver: */
00000982
00000983     master->mode_bits = SPI_CPOL | SPI_CPHA | SPI_CS_HIGH;
00000984
00000985     if (request_mem_region(mem_res->start,
00000986             resource_size(mem_res), pdev->name) == NULL) {
00000987         dev_err(&pdev->dev, "Req mem region failed\n");
00000988         ret = -ENXIO;
00000989         goto err0;
00000990     }
00000991
00000992     sdd->regs = ioremap(mem_res->start, resource_size(mem_res));
00000993     if (sdd->regs == NULL) {
00000994         dev_err(&pdev->dev, "Unable to remap IO\n");
00000995         ret = -ENXIO;
00000996         goto err1;
00000997     }
00000998
00000999     if (sci->cfg_gpio == NULL || sci->cfg_gpio(pdev)) {
00001000         dev_err(&pdev->dev, "Unable to config gpio\n");
00001001         ret = -EBUSY;
00001002         goto err2;
00001003     }
00001004
00001005     /* Setup clocks */
00001006     sdd->clk = clk_get(&pdev->dev, "spi");
00001007     if (IS_ERR(sdd->clk)) {
00001008         dev_err(&pdev->dev, "Unable to acquire clock 'spi'\n");
00001009         ret = PTR_ERR(sdd->clk);
00001010         goto err3;
00001011     }
00001012
00001013     if (clk_enable(sdd->clk)) {
00001014         dev_err(&pdev->dev, "Couldn't enable clock 'spi'\n");
00001015         ret = -EBUSY;
00001016         goto err4;
00001017     }
00001018
00001019     sdd->src_clk = clk_get(&pdev->dev, sci->src_clk_name);
00001020     if (IS_ERR(sdd->src_clk)) {
00001021         dev_err(&pdev->dev,
00001022             "Unable to acquire clock '%s'\n", sci->src_clk_name);
00001023         ret = PTR_ERR(sdd->src_clk);
00001024         goto err5;
00001025     }
00001026
00001027     if (clk_enable(sdd->src_clk)) {
00001028         dev_err(&pdev->dev, "Couldn't enable clock '%s'\n",
00001029                             sci->src_clk_name);
00001030         ret = -EBUSY;
00001031         goto err6;
00001032     }
00001033
00001034     sdd->workqueue = create_singlethread_workqueue(
00001035                         dev_name(master->dev.parent));
00001036     if (sdd->workqueue == NULL) {
00001037         dev_err(&pdev->dev, "Unable to create workqueue\n");
00001038         ret = -ENOMEM;
00001039         goto err7;
00001040     }
00001041
00001042     /* Setup Deufult Mode */
00001043     s3c64xx_spi_hwinit(sdd, pdev->id);
00001044
00001045     spin_lock_init(&sdd->lock);
00001046     init_completion(&sdd->xfer_completion);
00001047     INIT_WORK(&sdd->work, s3c64xx_spi_work);
00001048     INIT_LIST_HEAD(&sdd->queue);
00001049
00001050     if (spi_register_master(master)) {
00001051         dev_err(&pdev->dev, "cannot register SPI master\n");
00001052         ret = -EBUSY;
00001053         goto err8;
00001054     }
00001055
00001056     dev_dbg(&pdev->dev, "Samsung SoC SPI Driver loaded for Bus SPI-%d "
00001057                     "with %d Slaves attached\n",
00001058                     pdev->id, master->num_chipselect);
00001059     dev_dbg(&pdev->dev, "\tIOmem=[0x%x-0x%x]\tDMA=[Rx-%d, Tx-%d]\n",
00001060                     mem_res->end, mem_res->start,
00001061                     sdd->rx_dmach, sdd->tx_dmach);
00001062
00001063     return 0;
00001064
00001065 err8:
00001066     destroy_workqueue(sdd->workqueue);
00001067 err7:
00001068     clk_disable(sdd->src_clk);
00001069 err6:
00001070     clk_put(sdd->src_clk);
00001071 err5:
00001072     clk_disable(sdd->clk);
00001073 err4:
00001074     clk_put(sdd->clk);
00001075 err3:
00001076 err2:
00001077     iounmap((void *) sdd->regs);
00001078 err1:
00001079     release_mem_region(mem_res->start, resource_size(mem_res));
00001080 err0:
00001081     platform_set_drvdata(pdev, NULL);
00001082     spi_master_put(master);
00001083
00001084     return ret;
00001085 }

函数很长,但做的东西却很简单。919至923行,SPI控制器的ID是从0开始的,小于0的话,没门,出错。

925至928行,必须要有platform_data,否则出错。930行,如果platform_data存在的话就把它取出来。

931至935行,如果src_clk_name为0,则表示在板初始化函数里没有调用s3c64xx_spi_set_info函数。

939至955行,获取在设备里定义的IO口和DMA资源。

957至962行,一个SPI控制器用一个master来描述。这里使用SPI核心的spi_alloc_master函数请求分配master。它在drivers/spi/spi.c文件中定义:

00000471 struct spi_master *spi_alloc_master(struct device *dev, unsigned size)
00000472 {
00000473     struct spi_master    *master;
00000474
00000475     if (!dev)
00000476         return NULL;
00000477
00000478     master = kzalloc(size + sizeof *master, GFP_KERNEL);
00000479     if (!master)
00000480         return NULL;
00000481
00000482     device_initialize(&master->dev);
00000483     master->dev.class = &spi_master_class;
00000484     master->dev.parent = get_device(dev);
00000485     spi_master_set_devdata(master, &master[1]);
00000486
00000487     return master;
00000488 }

478至480行,这里分配的内存大小是*master加size,包含了两部分内存。

482行,设备模型中的初始设备函数,不说。

483行,spi_master_class在SPI子系统初始化的时候就已经注册好了。

484行,设置当前设备的父设备,关于设备模型的。

485行,&master[1]就是master之后的另一部分内存的起始地址。

回到s3c64xx_spi_probe函数,966行,就是取出刚才申请的第二部分内存的起始地址。

966至980行,根据预先定义的变量、函数进行填充。

983行,有点意思,说明该驱动支持哪些SPI模式。

985至997行,写过Linux驱动都应该知道,IO内存映射。

999至1003行,SPI IO管脚配置,将相应的IO管脚设置为SPI功能。

1006至1032行,使能SPI时钟。

1034至1040行,创建单个线程的工作队列,用于数据收发操作。

1043行,硬件初始化,初始化SPI控制器寄存器。

1045至1048行,锁,工作队列等初始化。

1050至1054行,spi_register_master在drivers/spi/spi.c文件中定义:

00000511 int spi_register_master(struct spi_master *master)
00000512 {
00000513     static atomic_t        dyn_bus_id = ATOMIC_INIT((1<<15) - 1);
00000514     struct device        *dev = master->dev.parent;
00000515     int            status = -ENODEV;
00000516     int            dynamic = 0;
00000517
00000518     if (!dev)
00000519         return -ENODEV;
00000520
00000521     /* even if it's just one always-selected device, there must
00000522      * be at least one chipselect
00000523      */
00000524     if (master->num_chipselect == 0)
00000525         return -EINVAL;
00000526
00000527     /* convention:  dynamically assigned bus IDs count down from the max */
00000528     if (master->bus_num < 0) {
00000529         /* FIXME switch to an IDR based scheme, something like
00000530          * I2C now uses, so we can't run out of "dynamic" IDs
00000531          */
00000532         master->bus_num = atomic_dec_return(&dyn_bus_id);
00000533         dynamic = 1;
00000534     }
00000535
00000536     spin_lock_init(&master->bus_lock_spinlock);
00000537     mutex_init(&master->bus_lock_mutex);
00000538     master->bus_lock_flag = 0;
00000539
00000540     /* register the device, then userspace will see it.
00000541      * registration fails if the bus ID is in use.
00000542      */
00000543     dev_set_name(&master->dev, "spi%u", master->bus_num);
00000544     status = device_add(&master->dev);
00000545     if (status < 0)
00000546         goto done;
00000547     dev_dbg(dev, "registered master %s%s\n", dev_name(&master->dev),
00000548             dynamic ? " (dynamic)" : "");
00000549
00000550     /* populate children from any spi device tables */
00000551     scan_boardinfo(master);
00000552     status = 0;
00000553
00000554     /* Register devices from the device tree */
00000555     of_register_spi_devices(master);
00000556 done:
00000557     return status;
00000558 }

524行,一个SPI控制器至少有一个片选,因此片选数为0则出错。

528至534行,如果总线号小于0则动态分配一个总线号。

543至548行,把master加入到设备模型中。

551行,scan_boardinfo函数同样是在driver/spi/spi.c中定义:

00000414 static void scan_boardinfo(struct spi_master *master)
00000415 {
00000416     struct boardinfo    *bi;
00000417
00000418     mutex_lock(&board_lock);
00000419     list_for_each_entry(bi, &board_list, list) {
00000420         struct spi_board_info    *chip = bi->board_info;
00000421         unsigned        n;
00000422
00000423         for (n = bi->n_board_info; n > 0; n--, chip++) {
00000424             if (chip->bus_num != master->bus_num)
00000425                 continue;
00000426             /* NOTE: this relies on spi_new_device to
00000427              * issue diagnostics when given bogus inputs
00000428              */
00000429             (void) spi_new_device(master, chip);
00000430         }
00000431     }
00000432     mutex_unlock(&board_lock);
00000433 }

419至431做了两件事情,首先遍历board_list这个链表,每找到一个成员就将它的总线号与master的总线号进行比较,如果相等则调用spi_new_device函数创建一个spi设备。

00000336 struct spi_device *spi_new_device(struct spi_master *master,
00000337                   struct spi_board_info *chip)
00000338 {
00000339     struct spi_device    *proxy;
00000340     int            status;
00000341
00000342     /* NOTE:  caller did any chip->bus_num checks necessary.
00000343      *
00000344      * Also, unless we change the return value convention to use
00000345      * error-or-pointer (not NULL-or-pointer), troubleshootability
00000346      * suggests syslogged diagnostics are best here (ugh).
00000347      */
00000348
00000349     proxy = spi_alloc_device(master);
00000350     if (!proxy)
00000351         return NULL;
00000352
00000353     WARN_ON(strlen(chip->modalias) >= sizeof(proxy->modalias));
00000354
00000355     proxy->chip_select = chip->chip_select;
00000356     proxy->max_speed_hz = chip->max_speed_hz;
00000357     proxy->mode = chip->mode;
00000358     proxy->irq = chip->irq;
00000359     strlcpy(proxy->modalias, chip->modalias, sizeof(proxy->modalias));
00000360     proxy->dev.platform_data = (void *) chip->platform_data;
00000361     proxy->controller_data = chip->controller_data;
00000362     proxy->controller_state = NULL;
00000363
00000364     status = spi_add_device(proxy);
00000365     if (status < 0) {
00000366         spi_dev_put(proxy);
00000367         return NULL;
00000368     }
00000369
00000370     return proxy;
00000371 }

349至351行,spi_alloc_device函数的定义:

00000229 struct spi_device *spi_alloc_device(struct spi_master *master)
00000230 {
00000231     struct spi_device    *spi;
00000232     struct device        *dev = master->dev.parent;
00000233
00000234     if (!spi_master_get(master))
00000235         return NULL;
00000236
00000237     spi = kzalloc(sizeof *spi, GFP_KERNEL);
00000238     if (!spi) {
00000239         dev_err(dev, "cannot alloc spi_device\n");
00000240         spi_master_put(master);
00000241         return NULL;
00000242     }
00000243
00000244     spi->master = master;
00000245     spi->dev.parent = dev;
00000246     spi->dev.bus = &spi_bus_type;
00000247     spi->dev.release = spidev_release;
00000248     device_initialize(&spi->dev);
00000249     return spi;
00000250 }

234至242行,错误检测和分配内存。

246行,该spi设备属于SPI子系统初始化时注册的那条叫“spi”的总线。

248行,设备模型方面的初始化,不说。

回到spi_new_device函数,355至362行,是一些赋值,其中359行比较关键,设备名字拷贝,362行,之前说过了,设置为NULL。看364行spi_add_device函数的定义:

00000262 int spi_add_device(struct spi_device *spi)
00000263 {
00000264     static DEFINE_MUTEX(spi_add_lock);
00000265     struct device *dev = spi->master->dev.parent;
00000266     struct device *d;
00000267     int status;
00000268
00000269     /* Chipselects are numbered 0..max; validate. */
00000270     if (spi->chip_select >= spi->master->num_chipselect) {
00000271         dev_err(dev, "cs%d >= max %d\n",
00000272             spi->chip_select,
00000273             spi->master->num_chipselect);
00000274         return -EINVAL;
00000275     }
00000276
00000277     /* Set the bus ID string */
00000278     dev_set_name(&spi->dev, "%s.%u", dev_name(&spi->master->dev),
00000279             spi->chip_select);
00000280
00000281
00000282     /* We need to make sure there's no other device with this
00000283      * chipselect **BEFORE** we call setup(), else we'll trash
00000284      * its configuration.  Lock against concurrent add() calls.
00000285      */
00000286     mutex_lock(&spi_add_lock);
00000287
00000288     d = bus_find_device_by_name(&spi_bus_type, NULL, dev_name(&spi->dev));
00000289     if (d != NULL) {
00000290         dev_err(dev, "chipselect %d already in use\n",
00000291                 spi->chip_select);
00000292         put_device(d);
00000293         status = -EBUSY;
00000294         goto done;
00000295     }
00000296
00000297     /* Drivers may modify this initial i/o setup, but will
00000298      * normally rely on the device being setup.  Devices
00000299      * using SPI_CS_HIGH can't coexist well otherwise...
00000300      */
00000301     status = spi_setup(spi);
00000302     if (status < 0) {
00000303         dev_err(dev, "can't %s %s, status %d\n",
00000304                 "setup", dev_name(&spi->dev), status);
00000305         goto done;
00000306     }
00000307
00000308     /* Device may be bound to an active driver when this returns */
00000309     status = device_add(&spi->dev);
00000310     if (status < 0)
00000311         dev_err(dev, "can't %s %s, status %d\n",
00000312                 "add", dev_name(&spi->dev), status);
00000313     else
00000314         dev_dbg(dev, "registered child %s\n", dev_name(&spi->dev));
00000315
00000316 done:
00000317     mutex_unlock(&spi_add_lock);
00000318     return status;
00000319 }

270至275行,片选号是从0开始的,如果大于或者等于片选数的话则返回出错。

288至295行,遍历spi总线,看是否已经注册过该设备。

301至306行,spi_setup函数的定义:

00000645 int spi_setup(struct spi_device *spi)
00000646 {
00000647     unsigned    bad_bits;
00000648     int        status;
00000649
00000650     /* help drivers fail *cleanly* when they need options
00000651      * that aren't supported with their current master
00000652      */
00000653     bad_bits = spi->mode & ~spi->master->mode_bits;
00000654     if (bad_bits) {
00000655         dev_dbg(&spi->dev, "setup: unsupported mode bits %x\n",
00000656             bad_bits);
00000657         return -EINVAL;
00000658     }
00000659
00000660     if (!spi->bits_per_word)
00000661         spi->bits_per_word = 8;
00000662
00000663     status = spi->master->setup(spi);
00000664
00000665     dev_dbg(&spi->dev, "setup mode %d, %s%s%s%s"
00000666                 "%u bits/w, %u Hz max --> %d\n",
00000667             (int) (spi->mode & (SPI_CPOL | SPI_CPHA)),
00000668             (spi->mode & SPI_CS_HIGH) ? "cs_high, " : "",
00000669             (spi->mode & SPI_LSB_FIRST) ? "lsb, " : "",
00000670             (spi->mode & SPI_3WIRE) ? "3wire, " : "",
00000671             (spi->mode & SPI_LOOP) ? "loopback, " : "",
00000672             spi->bits_per_word, spi->max_speed_hz,
00000673             status);
00000674
00000675     return status;
00000676 }

653至658行,如果驱动不支持该设备的工作模式则返回出错。

663行,调用控制器驱动里的s3c64xx_spi_setup函数,只看前一部分代码:

00000795 static int s3c64xx_spi_setup(struct spi_device *spi)
00000796 {
00000797     struct s3c64xx_spi_csinfo *cs = spi->controller_data;
00000798     struct s3c64xx_spi_driver_data *sdd;
00000799     struct s3c64xx_spi_info *sci;
00000800     struct spi_message *msg;
00000801     u32 psr, speed;
00000802     unsigned long flags;
00000803     int err = 0;
00000804
00000805     if (cs == NULL || cs->set_level == NULL) {
00000806         dev_err(&spi->dev, "No CS for SPI(%d)\n", spi->chip_select);
00000807         return -ENODEV;
00000808     }
00000809
…

从797行就可以知道在实例化struct spi_board_info时,其controller_data成员就应该指向struct s3c64xx_spi_csinfo的对象。

spi_setup函数结束了,回到spi_add_device函数,309至314行,将该设备加入到设备模型。一直后退,回到spi_register_master函数,就剩下555行of_register_spi_devices这个函数,由于本文所讲的驱动没有使用到设备树方面的内容,所以该函数里什么也没做,直接返回。

到这里,SPI控制器驱动的初始化过程已经说完了。接下来要说的是SPI设备驱动。其实Linux中已经实现了一个通用的SPI设备驱动,另外还有一个是用IO口模拟的SPI驱动,在这里,只说前者。

初始化函数是在drivers/spi/spidev.c文件中定义:

00000658 static int __init spidev_init(void)
00000659 {
00000660     int status;
00000661
00000662     /* Claim our 256 reserved device numbers.  Then register a class
00000663      * that will key udev/mdev to add/remove /dev nodes.  Last, register
00000664      * the driver which manages those device numbers.
00000665      */
00000666     BUILD_BUG_ON(N_SPI_MINORS > 256);
00000667
00000668     status = register_chrdev(SPIDEV_MAJOR, "spi", &spidev_fops);
00000669     if (status < 0)
00000670         return status;
00000671
00000672
00000673     spidev_class = class_create(THIS_MODULE, "spidev");
00000674     if (IS_ERR(spidev_class)) {
00000675         unregister_chrdev(SPIDEV_MAJOR, spidev_spi_driver.driver.name);
00000676         return PTR_ERR(spidev_class);
00000677     }
00000678
00000679     status = spi_register_driver(&spidev_spi_driver);
00000680     if (status < 0) {
00000681         class_destroy(spidev_class);
00000682         unregister_chrdev(SPIDEV_MAJOR, spidev_spi_driver.driver.name);
00000683     }
00000684     return status;
00000685 }

668至670行,注册字符设备,参数spidev_fops是struct file_operations的实例,这里就可以知道,用户程序的open、write等操作最终会调用这里面的函数。

673至677行,创建spidev这一类设备,为后面自动生成设备节点做准备。

679至684行,注册spi设备驱动spi_register_driver函数的定义在drivers/spi/spi.c中:

00000182 int spi_register_driver(struct spi_driver *sdrv)
00000183 {
00000184     sdrv->driver.bus = &spi_bus_type;
00000185     if (sdrv->probe)
00000186         sdrv->driver.probe = spi_drv_probe;
00000187     if (sdrv->remove)
00000188         sdrv->driver.remove = spi_drv_remove;
00000189     if (sdrv->shutdown)
00000190         sdrv->driver.shutdown = spi_drv_shutdown;
00000191     return driver_register(&sdrv->driver);
00000192 }

184行,该驱动所属的总线。185至190行,一些函数指针的赋值。191行,将驱动注册进设备模型,注册成功的话就会在总线上寻找设备,调用总线上的match函数,看能否与之匹配起来,匹配成功的话,驱动中的probe函数就会被调用。

参数spidev_spi_driver是struct spi_driver的实例,它的定义为:

00000641 static struct spi_driver spidev_spi_driver = {
00000642     .driver = {
00000643         .name =        "spidev",
00000644         .owner =    THIS_MODULE,
00000645     },
00000646     .probe =    spidev_probe,
00000647     .remove =    __devexit_p(spidev_remove),
00000648
00000649     /* NOTE:  suspend/resume methods are not necessary here.
00000650      * We don't do anything except pass the requests to/from
00000651      * the underlying controller.  The refrigerator handles
00000652      * most issues; the controller driver handles the rest.
00000653      */
00000654 };

下面看spidev_probe函数。在drivers/spi/spidev.c中定义的:

00000565 static int __devinit spidev_probe(struct spi_device *spi)
00000566 {
00000567     struct spidev_data    *spidev;
00000568     int            status;
00000569     unsigned long        minor;
00000570
00000571     /* Allocate driver data */
00000572     spidev = kzalloc(sizeof(*spidev), GFP_KERNEL);
00000573     if (!spidev)
00000574         return -ENOMEM;
00000575
00000576     /* Initialize the driver data */
00000577     spidev->spi = spi;
00000578     spin_lock_init(&spidev->spi_lock);
00000579     mutex_init(&spidev->buf_lock);
00000580
00000581     INIT_LIST_HEAD(&spidev->device_entry);
00000582
00000583     /* If we can allocate a minor number, hook up this device.
00000584      * Reusing minors is fine so long as udev or mdev is working.
00000585      */
00000586     mutex_lock(&device_list_lock);
00000587
00000588     minor = find_first_zero_bit(minors, N_SPI_MINORS);
00000589
00000590     if (minor < N_SPI_MINORS) {
00000591         struct device *dev;
00000592
00000593         spidev->devt = MKDEV(SPIDEV_MAJOR, minor);
00000594
00000595         dev = device_create(spidev_class, &spi->dev, spidev->devt,
00000596                     spidev, "spidev%d.%d",
00000597                     spi->master->bus_num, spi->chip_select);
00000598         status = IS_ERR(dev) ? PTR_ERR(dev) : 0;
00000599     } else {
00000600         dev_dbg(&spi->dev, "no minor number available!\n");
00000601         status = -ENODEV;
00000602     }
00000603     if (status == 0) {
00000604
00000605         set_bit(minor, minors);
00000606
00000607         list_add(&spidev->device_entry, &device_list);
00000608     }
00000609     mutex_unlock(&device_list_lock);
00000610
00000611     if (status == 0)
00000612         spi_set_drvdata(spi, spidev);
00000613     else
00000614         kfree(spidev);
00000615
00000616     return status;
00000617 }

572至574行,分配内存,注意对象的类型是struct spidev_data,看下它在drivers/spi/spidev.c中的定义:

00000075 struct spidev_data {
00000076     dev_t            devt;
00000077     spinlock_t        spi_lock;
00000078     struct spi_device    *spi;
00000079     struct list_head    device_entry;
00000080
00000081     /* buffer is NULL unless this device is open (users > 0) */
00000082     struct mutex        buf_lock;
00000083     unsigned        users;
00000084     u8            *buffer;
00000085 };

76行,设备号。79行,设备链表,所有采用此驱动的设备将连成一个链表。83行,计数,也即是此设备被open的次数。

回到spidev_probe函数,577至586行,一些锁和链表的初始化。588行,从名字上就可以知道,就是找到第一个为0的位,第一个参数minors的定义:

00000054 #define N_SPI_MINORS            32    /* ... up to 256 */
00000055
00000056 static DECLARE_BITMAP(minors, N_SPI_MINORS);

DECLARE_BITMAP是一个宏,定义如下:

#define DECLARE_BITMAP(name,bits) \unsigned long name[BITS_TO_LONGS(bits)]

将宏展开后是这样的,unsigned long minors[1],其实就是定义一个只有一个元素的无符号长整形数组miniors。

590至593行,如果找到了非0位,就将它作为次设备号与之前注册的主设备号生成设备号。

595至598行,创建设备,并生成设备节点,设备节点在/dev目录下,名字的形式为“spidevx.x”。

603至608行,创建设备成功后,将相应的位置1,表示该次设备号已经被使用,同时将该设备加入到设备链表。

611至614行,将设备的私有数据指针指向该设备。

至此,SPI设备驱动的初始化过程也说完了。下面就以应用程序的操作顺序来说,假设是从open-->write这个过程。下面先看驱动中open函数的实现,同样在drivers/spi/spidev.c:

00000477 static int spidev_open(struct inode *inode, struct file *filp)
00000478 {
00000479     struct spidev_data    *spidev;
00000480     int            status = -ENXIO;
00000481
00000482     mutex_lock(&device_list_lock);
00000483
00000484
00000485     list_for_each_entry(spidev, &device_list, device_entry) {
00000486         if (spidev->devt == inode->i_rdev) {
00000487             status = 0;
00000488             break;
00000489         }
00000490     }
00000491     if (status == 0) {
00000492         if (!spidev->buffer) {
00000493             spidev->buffer = kmalloc(bufsiz, GFP_KERNEL);
00000494             if (!spidev->buffer) {
00000495                 dev_dbg(&spidev->spi->dev, "open/ENOMEM\n");
00000496                 status = -ENOMEM;
00000497             }
00000498         }
00000499         if (status == 0) {
00000500             spidev->users++;
00000501             filp->private_data = spidev;
00000502             nonseekable_open(inode, filp);
00000503         }
00000504     } else
00000505         pr_debug("spidev: nothing for minor %d\n", iminor(inode));
00000506
00000507     mutex_unlock(&device_list_lock);
00000508     return status;
00000509 }

485至490行,遍历设备链表,每找到一个设备就将它的设备号与打开文件的设备号进行比较,相等的话表示查找成功。

491至505行,查找成功后就分配读写数据内存,使用计数加1,设置文件私有数据指针指向查找到的设备,以后在驱动的write、read函数里就可以把它取出来。

接下来是write函数的定义:

00000190 static ssize_t
00000191 spidev_write(struct file *filp, const char __user *buf,
00000192         size_t count, loff_t *f_pos)
00000193 {
00000194     struct spidev_data    *spidev;
00000195     ssize_t            status = 0;
00000196     unsigned long        missing;
00000197
00000198     /* chipselect only toggles at start or end of operation */
00000199     if (count > bufsiz)
00000200         return -EMSGSIZE;
00000201
00000202     spidev = filp->private_data;
00000203
00000204     mutex_lock(&spidev->buf_lock);
00000205     missing = copy_from_user(spidev->buffer, buf, count);
00000206     if (missing == 0) {
00000207         status = spidev_sync_write(spidev, count);
00000208     } else
00000209         status = -EFAULT;
00000210     mutex_unlock(&spidev->buf_lock);
00000211
00000212     return status;
00000213 }

199至200行,应用程序写入的数据不能大于驱动中缓冲区的大小,默认为4096个字节。

202行,指向文件的私有数据。

205行,拷贝用户空间的数据到内核空间。

207行,spidev_sync_write的定义:

00000130 static inline ssize_t
00000131 spidev_sync_write(struct spidev_data *spidev, size_t len)
00000132 {
00000133     struct spi_transfer    t = {
00000134             .tx_buf        = spidev->buffer,
00000135             .len        = len,
00000136         };
00000137     struct spi_message    m;
00000138
00000139     spi_message_init(&m);
00000140     spi_message_add_tail(&t, &m);
00000141     return spidev_sync(spidev, &m);
00000142 }

133行,struct spi_transfer的定义在include/linux/spi/spi.h:

00000427 struct spi_transfer {
00000428     /* it's ok if tx_buf == rx_buf (right?)
00000429      * for MicroWire, one buffer must be null
00000430      * buffers must work with dma_*map_single() calls, unless
00000431      *   spi_message.is_dma_mapped reports a pre-existing mapping
00000432      */
00000433     const void    *tx_buf;
00000434     void        *rx_buf;
00000435     unsigned    len;
00000436
00000437     dma_addr_t    tx_dma;
00000438     dma_addr_t    rx_dma;
00000439
00000440     unsigned    cs_change:1;
00000441     u8        bits_per_word;
00000442     u16        delay_usecs;
00000443     u32        speed_hz;
00000444
00000445     struct list_head transfer_list;
00000446 };

433至435行,发送、接收缓冲区和长度。437和438行,发送和接收的DMA地址。

440行,传输完成后是否改变片选信号。

441行,如果为0则使用驱动的默认值。

442行,传输完成后等待多长时间(毫秒)再改变片选信号。

443行,将多个传输连成一个链表。

回到spidev_sync_write函数的137行,在spi.h中定义的struct spi_message

00000476 struct spi_message {
00000477     struct list_head    transfers;
00000478
00000479     struct spi_device    *spi;
00000480
00000481     unsigned        is_dma_mapped:1;
00000482
00000483     /* REVISIT:  we might want a flag affecting the behavior of the
00000484      * last transfer ... allowing things like "read 16 bit length L"
00000485      * immediately followed by "read L bytes".  Basically imposing
00000486      * a specific message scheduling algorithm.
00000487      *
00000488      * Some controller drivers (message-at-a-time queue processing)
00000489      * could provide that as their default scheduling algorithm.  But
00000490      * others (with multi-message pipelines) could need a flag to
00000491      * tell them about such special cases.
00000492      */
00000493
00000494     /* completion is reported through a callback */
00000495     void            (*complete)(void *context);
00000496     void            *context;
00000497     unsigned        actual_length;
00000498     int            status;
00000499
00000500     /* for optional use by whatever driver currently owns the
00000501      * spi_message ...  between calls to spi_async and then later
00000502      * complete(), that's the spi_master controller driver.
00000503      */
00000504     struct list_head    queue;
00000505     void            *state;
00000506 };

477行,一个message可能包含多个transfer,因此用链表将这些transfer连起来。

479行,这次message所使用的spi设备。

481行,是否采用DMA的标志。

495行,传输完成后的回调函数指针。496行,回调函数的参数。

497行,这次message成功传输的字节数。

504和505行,当前驱动拥有的message。

回到spidev_sync_write函数,139行,spi.h中的内联函数spi_message_init:

00000508 static inline void spi_message_init(struct spi_message *m)
00000509 {
00000510     memset(m, 0, sizeof *m);
00000511     INIT_LIST_HEAD(&m->transfers);
00000512 }

很简单,清0内存和初始化message的transfer链表。

140行,spi_message_add_tail也是spi.h中的内联函数:

00000514 static inline void
00000515 spi_message_add_tail(struct spi_transfer *t, struct spi_message *m)
00000516 {
00000517     list_add_tail(&t->transfer_list, &m->transfers);
00000518 }

将transfer加入到链表尾。

141行,spidev_sync函数是在drivers/spi/spidev.c中定义的:

00000105 static ssize_t
00000106 spidev_sync(struct spidev_data *spidev, struct spi_message *message)
00000107 {
00000108     DECLARE_COMPLETION_ONSTACK(done);
00000109     int status;
00000110
00000111     message->complete = spidev_complete;
00000112     message->context = &done;
00000113
00000114     spin_lock_irq(&spidev->spi_lock);
00000115     if (spidev->spi == NULL)
00000116         status = -ESHUTDOWN;
00000117     else
00000118         status = spi_async(spidev->spi, message);
00000119     spin_unlock_irq(&spidev->spi_lock);
00000120
00000121     if (status == 0) {
00000122         wait_for_completion(&done);
00000123         status = message->status;
00000124         if (status == 0)
00000125             status = message->actual_length;
00000126     }
00000127     return status;
00000128 }

108行,定义并初始化一个完成量,完成量是Linux的一种同步机制。

111行,spidev_complete函数里就用来唤醒等待completion,定义如下:

00000100 static void spidev_complete(void *arg)
00000101 {
00000102     complete(arg);
00000103 }

112行,作为spidev_complete函数的参数。

118行,调用drivers/spi/spi.c里的spi_async函数,从函数名知道,这是异步实现的。为什么是异步的?往下看就知道了。

00000737 int spi_async(struct spi_device *spi, struct spi_message *message)
00000738 {
00000739     struct spi_master *master = spi->master;
00000740     int ret;
00000741     unsigned long flags;
00000742
00000743     spin_lock_irqsave(&master->bus_lock_spinlock, flags);
00000744
00000745     if (master->bus_lock_flag)
00000746         ret = -EBUSY;
00000747     else
00000748         ret = __spi_async(spi, message);
00000749
00000750     spin_unlock_irqrestore(&master->bus_lock_spinlock, flags);
00000751
00000752     return ret;
00000753 }

745行,如果master所在的总线被锁住了,那么就返回忙。

748行,看__spi_async函数的定义:

00000679 static int __spi_async(struct spi_device *spi, struct spi_message *message)
00000680 {
00000681     struct spi_master *master = spi->master;
00000682
00000683     /* Half-duplex links include original MicroWire, and ones with
00000684      * only one data pin like SPI_3WIRE (switches direction) or where
00000685      * either MOSI or MISO is missing.  They can also be caused by
00000686      * software limitations.
00000687      */
00000688     if ((master->flags & SPI_MASTER_HALF_DUPLEX)
00000689             || (spi->mode & SPI_3WIRE)) {
00000690         struct spi_transfer *xfer;
00000691         unsigned flags = master->flags;
00000692
00000693         list_for_each_entry(xfer, &message->transfers, transfer_list) {
00000694             if (xfer->rx_buf && xfer->tx_buf)
00000695                 return -EINVAL;
00000696             if ((flags & SPI_MASTER_NO_TX) && xfer->tx_buf)
00000697                 return -EINVAL;
00000698             if ((flags & SPI_MASTER_NO_RX) && xfer->rx_buf)
00000699                 return -EINVAL;
00000700         }
00000701     }
00000702
00000703     message->spi = spi;
00000704     message->status = -EINPROGRESS;
00000705     return master->transfer(spi, message);
00000706 }

688至701行,如果master设置了SPI_MASTER_HALF_DUPLEX标志,或者spi设备使用的是3线模式,那么就对message里的每一个transfer的发送和接收buf做一些检查。

705行,调用的是具体的SPI控制器驱动里的函数,这里是drivers/spi/spi_s3c64xx.c里的s3c64xx_spi_transfer函数:

00000763 static int s3c64xx_spi_transfer(struct spi_device *spi,
00000764                         struct spi_message *msg)
00000765 {
00000766     struct s3c64xx_spi_driver_data *sdd;
00000767     unsigned long flags;
00000768
00000769     sdd = spi_master_get_devdata(spi->master);
00000770
00000771     spin_lock_irqsave(&sdd->lock, flags);
00000772
00000773     if (sdd->state & SUSPND) {
00000774         spin_unlock_irqrestore(&sdd->lock, flags);
00000775         return -ESHUTDOWN;
00000776     }
00000777
00000778     msg->status = -EINPROGRESS;
00000779     msg->actual_length = 0;
00000780
00000781     list_add_tail(&msg->queue, &sdd->queue);
00000782
00000783     queue_work(sdd->workqueue, &sdd->work);
00000784
00000785     spin_unlock_irqrestore(&sdd->lock, flags);
00000786
00000787     return 0;
00000788 }

781行之前没什么好说的,直接看783行,将work投入到工作队列里,然后就返回,在这里就可以回答之前为什么是异步的问题。以后在某个合适的时间里CPU会执行这个work指定的函数,这里是s3c64xx_spi_work函数,看它的定义:

00000723 static void s3c64xx_spi_work(struct work_struct *work)
00000724 {
00000725     struct s3c64xx_spi_driver_data *sdd = container_of(work,
00000726                     struct s3c64xx_spi_driver_data, work);
00000727     unsigned long flags;
00000728
00000729     /* Acquire DMA channels */
00000730     while (!acquire_dma(sdd))
00000731         msleep(10);
00000732
00000733     spin_lock_irqsave(&sdd->lock, flags);
00000734
00000735     while (!list_empty(&sdd->queue)
00000736                 && !(sdd->state & SUSPND)) {
00000737
00000738         struct spi_message *msg;
00000739
00000740         msg = container_of(sdd->queue.next, struct spi_message, queue);
00000741
00000742         list_del_init(&msg->queue);
00000743
00000744         /* Set Xfer busy flag */
00000745         sdd->state |= SPIBUSY;
00000746
00000747         spin_unlock_irqrestore(&sdd->lock, flags);
00000748
00000749         handle_msg(sdd, msg);
00000750
00000751         spin_lock_irqsave(&sdd->lock, flags);
00000752
00000753         sdd->state &= ~SPIBUSY;
00000754     }
00000755
00000756     spin_unlock_irqrestore(&sdd->lock, flags);
00000757
00000758     /* Free DMA channels */
00000759     s3c2410_dma_free(sdd->tx_dmach, &s3c64xx_spi_dma_client);
00000760     s3c2410_dma_free(sdd->rx_dmach, &s3c64xx_spi_dma_client);
00000761 }

730行,申请DMA,关于DMA的就不说,一是我对DMA没什么了解,二是这里基本上用不到,后面就知道什么时候才会用到DMA。

735至754行,循环取出队列里的message并调用749行的handle_msg函数进行处理,handle_msg函数的定义如下:

00000568 static void handle_msg(struct s3c64xx_spi_driver_data *sdd,
00000569                     struct spi_message *msg)
00000570 {
00000571     struct s3c64xx_spi_info *sci = sdd->cntrlr_info;
00000572     struct spi_device *spi = msg->spi;
00000573     struct s3c64xx_spi_csinfo *cs = spi->controller_data;
00000574     struct spi_transfer *xfer;
00000575     int status = 0, cs_toggle = 0;
00000576     u32 speed;
00000577     u8 bpw;
00000578
00000579     /* If Master's(controller) state differs from that needed by Slave */
00000580     if (sdd->cur_speed != spi->max_speed_hz
00000581             || sdd->cur_mode != spi->mode
00000582             || sdd->cur_bpw != spi->bits_per_word) {
00000583         sdd->cur_bpw = spi->bits_per_word;
00000584         sdd->cur_speed = spi->max_speed_hz;
00000585         sdd->cur_mode = spi->mode;
00000586         s3c64xx_spi_config(sdd);
00000587     }
00000588
00000589     /* Map all the transfers if needed */
00000590     if (s3c64xx_spi_map_mssg(sdd, msg)) {
00000591         dev_err(&spi->dev,
00000592             "Xfer: Unable to map message buffers!\n");
00000593         status = -ENOMEM;
00000594         goto out;
00000595     }
00000596
00000597     /* Configure feedback delay */
00000598     writel(cs->fb_delay & 0x3, sdd->regs + S3C64XX_SPI_FB_CLK);
00000599
00000600     list_for_each_entry(xfer, &msg->transfers, transfer_list) {
00000601
00000602         unsigned long flags;
00000603         int use_dma;
00000604
00000605         INIT_COMPLETION(sdd->xfer_completion);
00000606
00000607         /* Only BPW and Speed may change across transfers */
00000608         bpw = xfer->bits_per_word ? : spi->bits_per_word;
00000609         speed = xfer->speed_hz ? : spi->max_speed_hz;
00000610
00000611         if (bpw != sdd->cur_bpw || speed != sdd->cur_speed) {
00000612             sdd->cur_bpw = bpw;
00000613             sdd->cur_speed = speed;
00000614             s3c64xx_spi_config(sdd);
00000615         }
00000616
00000617         /* Polling method for xfers not bigger than FIFO capacity */
00000618
00000619         if (xfer->len <= ((sci->fifo_lvl_mask >> 1) + 1))
00000620             use_dma = 0;
00000621         else
00000622             use_dma = 1;
00000623
00000624         spin_lock_irqsave(&sdd->lock, flags);
00000625
00000626         /* Pending only which is to be done */
00000627         sdd->state &= ~RXBUSY;
00000628         sdd->state &= ~TXBUSY;
00000629
00000630         enable_datapath(sdd, spi, xfer, use_dma);
00000631
00000632         /* Slave Select */
00000633         enable_cs(sdd, spi);
00000634
00000635         /* Start the signals */
00000636         S3C64XX_SPI_ACT(sdd);
00000637
00000638         spin_unlock_irqrestore(&sdd->lock, flags);
00000639
00000640         status = wait_for_xfer(sdd, xfer, use_dma);
00000641
00000642         /* Quiese the signals */
00000643         S3C64XX_SPI_DEACT(sdd);
00000644
00000645         if (status) {
00000646             dev_err(&spi->dev, "I/O Error: "
00000647                 "rx-%d tx-%d res:rx-%c tx-%c len-%d\n",
00000648                 xfer->rx_buf ? 1 : 0, xfer->tx_buf ? 1 : 0,
00000649                 (sdd->state & RXBUSY) ? 'f' : 'p',
00000650                 (sdd->state & TXBUSY) ? 'f' : 'p',
00000651                 xfer->len);
00000652
00000653             if (use_dma) {
00000654                 if (xfer->tx_buf != NULL
00000655                         && (sdd->state & TXBUSY))
00000656                     s3c2410_dma_ctrl(sdd->tx_dmach,
00000657                             S3C2410_DMAOP_FLUSH);
00000658                 if (xfer->rx_buf != NULL
00000659                         && (sdd->state & RXBUSY))
00000660                     s3c2410_dma_ctrl(sdd->rx_dmach,
00000661                             S3C2410_DMAOP_FLUSH);
00000662             }
00000663
00000664             goto out;
00000665         }
00000666
00000667         if (xfer->delay_usecs)
00000668             udelay(xfer->delay_usecs);
00000669
00000670         if (xfer->cs_change) {
00000671             /* Hint that the next mssg is gonna be
00000672                for the same device */
00000673             if (list_is_last(&xfer->transfer_list,
00000674                         &msg->transfers))
00000675                 cs_toggle = 1;
00000676             else
00000677                 disable_cs(sdd, spi);
00000678         }
00000679
00000680         msg->actual_length += xfer->len;
00000681
00000682         flush_fifo(sdd);
00000683     }
00000684
00000685 out:
00000686     if (!cs_toggle || status)
00000687         disable_cs(sdd, spi);
00000688     else
00000689         sdd->tgl_spi = spi;
00000690
00000691     s3c64xx_spi_unmap_mssg(sdd, msg);
00000692
00000693     msg->status = status;
00000694
00000695     if (msg->complete)
00000696         msg->complete(msg->context);
00000697 }

函数很长,580至587行,如果一路走来speed、bpw和mode的值与spi设备的不一致就调用s3c64xx_spi_config函数重新配置,s3c64xx_spi_config函数里面就是对SPI寄存器进行设置的。

590至595行,关于DMA映射的,略过。

598行,设置feedback寄存器。

600行,遍历每一个transfer。605行,又初始化一个完成量,注意这里与之前的那个完成量是不一样的,这里的完成量只有使用DMA传输时才会用得到,接下来很快就可以看到。

608至615行,也是一些关于设置值的检查。

619至622行,只有发送或者接收的数据长度大于fifo的深度(这里是64个字节)设置use_dma为1,也即使用DMA进行传输,否则不使用DMA。

630行,enable_datapath函数的定义为:

00000232 static void enable_datapath(struct s3c64xx_spi_driver_data *sdd,
00000233                 struct spi_device *spi,
00000234                 struct spi_transfer *xfer, int dma_mode)
00000235 {
00000236     struct s3c64xx_spi_info *sci = sdd->cntrlr_info;
00000237     void __iomem *regs = sdd->regs;
00000238     u32 modecfg, chcfg;
00000239
00000240     modecfg = readl(regs + S3C64XX_SPI_MODE_CFG);
00000241     modecfg&=~(S3C64XX_SPI_MODE_TXDMA_ON|S3C64XX_SPI_MODE_RXDMA_ON);
00000242
00000243     chcfg = readl(regs + S3C64XX_SPI_CH_CFG);
00000244     chcfg &= ~S3C64XX_SPI_CH_TXCH_ON;
00000245
00000246     if (dma_mode) {
00000247         chcfg &= ~S3C64XX_SPI_CH_RXCH_ON;
00000248     } else {
00000249         /* Always shift in data in FIFO, even if xfer is Tx only,
00000250          * this helps setting PCKT_CNT value for generating clocks
00000251          * as exactly needed.
00000252          */
00000253         chcfg |= S3C64XX_SPI_CH_RXCH_ON;
00000254         writel(((xfer->len * 8 / sdd->cur_bpw) & 0xffff)
00000255                     | S3C64XX_SPI_PACKET_CNT_EN,
00000256                     regs + S3C64XX_SPI_PACKET_CNT);
00000257     }
00000258
00000259     if (xfer->tx_buf != NULL) {
00000260         sdd->state |= TXBUSY;
00000261         chcfg |= S3C64XX_SPI_CH_TXCH_ON;
00000262         if (dma_mode) {
00000263             modecfg |= S3C64XX_SPI_MODE_TXDMA_ON;
00000264             s3c2410_dma_config(sdd->tx_dmach, 1);
00000265             s3c2410_dma_enqueue(sdd->tx_dmach, (void *)sdd,
00000266                         xfer->tx_dma, xfer->len);
00000267             s3c2410_dma_ctrl(sdd->tx_dmach, S3C2410_DMAOP_START);
00000268         } else {
00000269             unsigned char *buf = (unsigned char *) xfer->tx_buf;
00000270             int i = 0;
00000271             while (i < xfer->len)
00000272                 writeb(buf[i++], regs + S3C64XX_SPI_TX_DATA);
00000273         }
00000274     }
00000275
00000276     if (xfer->rx_buf != NULL) {
00000277         sdd->state |= RXBUSY;
00000278
00000279         if (sci->high_speed && sdd->cur_speed >= 30000000UL
00000280                     && !(sdd->cur_mode & SPI_CPHA))
00000281             chcfg |= S3C64XX_SPI_CH_HS_EN;
00000282
00000283         if (dma_mode) {
00000284             modecfg |= S3C64XX_SPI_MODE_RXDMA_ON;
00000285             chcfg |= S3C64XX_SPI_CH_RXCH_ON;
00000286             writel(((xfer->len * 8 / sdd->cur_bpw) & 0xffff)
00000287                     | S3C64XX_SPI_PACKET_CNT_EN,
00000288                     regs + S3C64XX_SPI_PACKET_CNT);
00000289             s3c2410_dma_config(sdd->rx_dmach, 1);
00000290             s3c2410_dma_enqueue(sdd->rx_dmach, (void *)sdd,
00000291                         xfer->rx_dma, xfer->len);
00000292             s3c2410_dma_ctrl(sdd->rx_dmach, S3C2410_DMAOP_START);
00000293         }
00000294     }
00000295
00000296     writel(modecfg, regs + S3C64XX_SPI_MODE_CFG);
00000297     writel(chcfg, regs + S3C64XX_SPI_CH_CFG);
00000298 }

240至244行,读取模式配置和通道配置寄存器。

246至257行,根据是否采用DMA模式设置接收计数寄存器。

259行,很早就为tx_buf分配内存,因此条件成立。因为不考虑DMA模式,因此略过262至268行。

269至272行,循环将发送数据写入到发送寄存器。

276至294行,由于rx_buf为NULL,因此直接略过277至294行。

296、297行,将之前的值写入到寄存器中。

回到handle_msg函数,633行,选中从设备。636行,设置寄存器,开始数据传输。

640行,wait_for_xfer函数的定义:

00000319 static int wait_for_xfer(struct s3c64xx_spi_driver_data *sdd,
00000320                 struct spi_transfer *xfer, int dma_mode)
00000321 {
00000322     struct s3c64xx_spi_info *sci = sdd->cntrlr_info;
00000323     void __iomem *regs = sdd->regs;
00000324     unsigned long val;
00000325     int ms;
00000326
00000327     /* millisecs to xfer 'len' bytes @ 'cur_speed' */
00000328     ms = xfer->len * 8 * 1000 / sdd->cur_speed;
00000329     ms += 10; /* some tolerance */
00000330
00000331     if (dma_mode) {
00000332         val = msecs_to_jiffies(ms) + 10;
00000333         val = wait_for_completion_timeout(&sdd->xfer_completion, val);
00000334     } else {
00000335         u32 status;
00000336         val = msecs_to_loops(ms);
00000337         do {
00000338             status = readl(regs + S3C64XX_SPI_STATUS);
00000339         } while (RX_FIFO_LVL(status, sci) < xfer->len && --val);
00000340     }
00000341
00000342     if (!val)
00000343         return -EIO;
00000344
00000345     if (dma_mode) {
00000346         u32 status;
00000347
00000348         /*
00000349          * DmaTx returns after simply writing data in the FIFO,
00000350          * w/o waiting for real transmission on the bus to finish.
00000351          * DmaRx returns only after Dma read data from FIFO which
00000352          * needs bus transmission to finish, so we don't worry if
00000353          * Xfer involved Rx(with or without Tx).
00000354          */
00000355         if (xfer->rx_buf == NULL) {
00000356             val = msecs_to_loops(10);
00000357             status = readl(regs + S3C64XX_SPI_STATUS);
00000358             while ((TX_FIFO_LVL(status, sci)
00000359                 || !S3C64XX_SPI_ST_TX_DONE(status, sci))
00000360                     && --val) {
00000361                 cpu_relax();
00000362                 status = readl(regs + S3C64XX_SPI_STATUS);
00000363             }
00000364
00000365             if (!val)
00000366                 return -EIO;
00000367         }
00000368     } else {
00000369         unsigned char *buf;
00000370         int i;
00000371
00000372         /* If it was only Tx */
00000373         if (xfer->rx_buf == NULL) {
00000374             sdd->state &= ~TXBUSY;
00000375             return 0;
00000376         }
00000377
00000378         i = 0;
00000379         buf = xfer->rx_buf;
00000380         while (i < xfer->len)
00000381             buf[i++] = readb(regs + S3C64XX_SPI_RX_DATA);
00000382
00000383         sdd->state &= ~RXBUSY;
00000384     }
00000385
00000386     return 0;
00000387 }

328行,根据发送速率计算需要等待的时间。331至334行,与DMA相关的,略过。

335至339行,不断地读状态寄存器,如果接收到的数据长度等于发送数据的长度或超时则退出循环。

342、343行,如果是超时退出循环的,则返回出错。

345至368行,DMA相关的,略过。

369至383行,如果只是发送数据,则直接返回0。否则从接收寄存器里将接收到的数据读出来。

回到handle_msg函数,643行,停止传输。645至665行,如果之前wait_for_xfer函数返回大于0的值,则表示出错,这里就打印一些信息。

667、668行,之前如果有设置延时的话这里就延时。

670至678行,是否需要每个transfer完成都改变片选信号。

680行,累加所有transfer成功发送的数据。

682行,清发送和接收寄存器。

691行,取消DMA映射。

693行,记录状态信息。

695、696行,唤醒之前等待的完成量。

到这里,已经说了整个write过程,不容易啊!。其他的read/ioctl过程是大同小异的。

总结

spidev.c是一个通用的SPI驱动,因此它不处理任何有关具体驱动的逻辑,这就需要在用户空间来完成具体的逻辑。其实这符合了Android驱动的思想,这也是Android HAL层存在的目的:内核驱动只完成硬件操作,具体逻辑放在HAL层,这样就有利于保护厂家、开发者的知识产权。

在用户空间使用ioctl就可以完成write、read操作。

二十、SPI设备驱动及应用(一)相关推荐

  1. (二)Linux设备驱动的模块化编程

    本系列导航 (一)初识Linux驱动 (二)Linux设备驱动的模块化编程 (三)写一个完整的Linux驱动程序访问硬件并写应用程序进行测试 (四)Linux设备驱动之多个同类设备共用一套驱动 (五) ...

  2. Linux SPI设备驱动

    实现了SPI OLED外设驱动,OLED型号为SH1106. 1.主机驱动与外设驱动分离 Linux中的I2C.SPI.USB等总线驱动,都采用了主机(控制器)驱动与外设(设备)驱动分离的思想.主机端 ...

  3. imx6ul spi 设备驱动开发

    imx6ul spi 设备驱动开发 spi设备树格式 spi设备树配置 spi 驱动 设备树解析 spi设备驱动使用 spi通用设备驱动 spi测试工具 spi时序对比 spi api 接口 spi设 ...

  4. platform框架--Linux MISC杂项框架--Linux INPUT子系统框架--串行集成电路总线I2C设备驱动框架--串行外设接口SPI 设备驱动框架---通用异步收发器UART驱动框架

    platform框架 input. pinctrl. gpio 子系统都是 Linux 内核针对某一类设备而创建的框架, input子系统是管理输入的子系统 pinctrl 子系统重点是设置 PIN( ...

  5. Linux I2C总线(二)I2C设备驱动编写方法

    Linux I2C总线 Linux I2C总线(一)I2C驱动框架 Linux I2C总线(二)I2C设备驱动编写方法 Linux I2C总线(二)I2C设备驱动编写方法 文章目录 Linux I2C ...

  6. RT-Thread (2) RTT SPI设备驱动流程 || LWIP + ENC28J60

    系列文章目录 RT-Thread (1) 添加外部内存到内存管理 RT-Thread (2) RTT SPI设备驱动流程 || LWIP + ENC28J60 RT-Thread (3) 为RTT增加 ...

  7. 驱动程序开发:SPI设备驱动

    目录 Linux下SPI驱动简介 SPI架构概述 SPI适配器(控制器) SPI设备驱动 spi_driver注册示例 SPI 设备和驱动匹配过程 编写imc20608六轴传感器SPI驱动 设备树编写 ...

  8. Linux kernel SPI源码分析之SPI设备驱动源码分析(linux kernel 5.18)

    SPI基础支持此处不再赘述,直接分析linux中的SPI驱动源码. 1.SPI设备驱动架构图 2.源码分析 本次分析基于kernel5.18,linux/drivers/spi/spidev.c 设备 ...

  9. LINUX SPI设备驱动模型分析之二 SPI总线模块分析

    上一篇文章我们简要介绍了SPI驱动模块,本章我们详细说明一下spi总线.设备.驱动模块的注册.注销以及这几个模块之间的关联. SPI总线的注册 spi模块也是基于LINUX设备-总线-驱动模型进行开发 ...

最新文章

  1. Ubuntu 无界面使用selenium chrome + headless
  2. java提高篇(三十)-----Iterator
  3. 讨论是学习最有效的方法
  4. c语言五子棋卡死,五子棋程序出错了
  5. 请求库-selenium 模块
  6. stm32f407网页服务器,STM32F407单片机通过USR-LTE-7S4模块和服务器进行4G通信
  7. mac php gd(mac osx 10.9.4)
  8. 聊聊Spring家族中的那几百个注解
  9. vue可拖动可放大div_麻省理工研发超级信号放大器,可将WiFi放大10倍
  10. 【带权并查集题目汇总】
  11. linux操作系统实验目的,Linux操作系统实验报告.doc
  12. vivado使用方法
  13. macOS Catalina 10.15.7 ISO/CDR 虚拟机镜像下载
  14. 神鬼传奇客户端解包图片(ui\common)
  15. python爬虫实践——爬取豆瓣电影排行榜
  16. vCenter 6.0 web访问503错误:服务不可用,无法连接endpoint,
  17. Unity导航小地图制作
  18. magic winmail邮件服务器,使用Magic Winmail Server轻松架设邮件服务器(一)-网管专栏,邮件服务...
  19. Lagrange插值法
  20. adb 清理内存_Android实现仿360桌面悬浮清理内存

热门文章

  1. [翻译] RKCardView
  2. Invoke shell in Java
  3. 图解VC++2012编译安装GDAL1.11.0和入门例子
  4. webpack 零基础到工程实战(1)
  5. MB_SELECT_GR_BLOCKED_STOCK 读取物料收货冻结库存
  6. Ubuntu下搜狗输入法乱码(二)
  7. Python3学习笔记——类
  8. 在Vista操作系统中通过manifest文件使VC应用程序获得管理员权限
  9. 软件测试之Selenium IDE
  10. bzoj 2186: [Sdoi2008]沙拉公主的困惑