接上一個繼續看spi.c。
-------------------------------
匹配設備 /* 名詞解釋of: OpenFirmware * 調用層次spi_match_device-->of_driver_match_device-->of_match_device--> * of_match_node * 用於驅動程序檢查platform_device是否在其支持列表裏 */ 80static int spi_match_device(struct device *dev, struct device_driver *drv) 81{ 82 const struct spi_device *spi = to_spi_device(dev); 83 const struct spi_driver *sdrv = to_spi_driver(drv); 84 85 /* Attempt an OF style match */ /* 不匹配返回0;匹配返回非0,指向struct of_device_id類型的指針 * dev:需要查找的設備; drv:驅動程序結構體 */ 86 if (of_driver_match_device(dev, drv)) 87 return 1; 88 /* 在驅動查找設備ID,找到返回真,否則假 */ 89 if (sdrv->id_table) 90 return !!spi_match_id(sdrv->id_table, spi); 91 /* 比較設備別名和驅動名稱,匹配返回真 */ 92 return strcmp(spi->modalias, drv->name) == 0; 93} 94
-------------------------------
uevent /* struct kobj_uevent_env 是內核用戶空間的一個環境參數 * uevent是sysfs向用戶空間發出的消息,這裏實際上添加的是一串字符串消息。 * 關於uevent參考:http://blog.csdn.net/walkingman321/archive/2010/10/01/5917737.aspx */ 95static int spi_uevent(struct device *dev, struct kobj_uevent_env *env) 96{ 97 const struct spi_device *spi = to_spi_device(dev); 98 99 add_uevent_var(env, "MODALIAS=%s%s", SPI_MODULE_PREFIX, spi->modalias); 100 return 0; 101}
-------------------------------
電源管理 /* 配置了電源管理 * 現在不清楚suspend和resume函數哪裏實現,等找到了再說 */ 103#ifdef CONFIG_PM 104 /* 掛起 */ 105static int spi_suspend(struct device *dev, pm_message_t message) 106{ 107 int value = 0; 108 struct spi_driver *drv = to_spi_driver(dev->driver); 109 110 /* suspend will stop irqs and dma; no more i/o */ /* 掛起將定製終端和DMA,沒有輸入輸出 */ 111 if (drv) { /* 驅動實現了掛起操作函數 */ 112 if (drv->suspend) 113 value = drv->suspend(to_spi_device(dev), message); 114 else 115 dev_dbg(dev, "... can't suspend/n"); 116 } 117 return value; 118} 119 /* 恢復 */ 120static int spi_resume(struct device *dev) 121{ 122 int value = 0; 123 struct spi_driver *drv = to_spi_driver(dev->driver); 124 125 /* resume may restart the i/o queue */ /* 重新開始輸入輸出隊列 */ 126 if (drv) { 127 if (drv->resume) 128 value = drv->resume(to_spi_device(dev)); 129 else 130 dev_dbg(dev, "... can't resume/n"); 131 } 132 return value; 133} 134 135#else /* 沒有電源管理 */ 136#define spi_suspend NULL 137#define spi_resume NULL 138#endif
-------------------------------
總線 /* 總線 參考:http://hi.baidu.com/xingzuzi/blog/item/d12c03f473b3c2a0a50f5260.html */ 140struct bus_type spi_bus_type = { 141 .name = "spi", 142 .dev_attrs = spi_dev_attrs, 143 .match = spi_match_device, 144 .uevent = spi_uevent, 145 .suspend = spi_suspend, 146 .resume = spi_resume, 147}; 148EXPORT_SYMBOL_GPL(spi_bus_type);
-------------------------------
驅動註冊、刪除 /* 驅動註冊 */ 151static int spi_drv_probe(struct device *dev) 152{ 153 const struct spi_driver *sdrv = to_spi_driver(dev->driver); 154 155 return sdrv->probe(to_spi_device(dev)); 156} 157 /* 驅動刪除 */ 158static int spi_drv_remove(struct device *dev) 159{ 160 const struct spi_driver *sdrv = to_spi_driver(dev->driver); 161 162 return sdrv->remove(to_spi_device(dev)); 163} 164 /* 關閉 */ 165static void spi_drv_shutdown(struct device *dev) 166{ 167 const struct spi_driver *sdrv = to_spi_driver(dev->driver); 168 169 sdrv->shutdown(to_spi_device(dev)); 170}
-------------------------------
註冊SPI總線驅動 /* 註冊SPI驅動 */ 172/** 173 * spi_register_driver - register a SPI driver 174 * @sdrv: the driver to register 175 * Context: can sleep 176 */ 177int spi_register_driver(struct spi_driver *sdrv) 178{ /* 初始化總線結構體 */ 179 sdrv->driver.bus = &spi_bus_type; /* 初始化驅動相關函數 */ 180 if (sdrv->probe) 181 sdrv->driver.probe = spi_drv_probe; 182 if (sdrv->remove) 183 sdrv->driver.remove = spi_drv_remove; 184 if (sdrv->shutdown) 185 sdrv->driver.shutdown = spi_drv_shutdown; /* 驅動註冊 * 添加驅動到總線 * sysfs、uevent等創建、初始化 */ 186 return driver_register(&sdrv->driver); 187} 188EXPORT_SYMBOL_GPL(spi_register_driver);
-------------------------------
今天先到這了。。。明天繼續
-------------------------------