sub_lens.c 8.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385
  1. /*
  2. * SUB AF voice coil motor driver
  3. *
  4. *
  5. */
  6. #include <linux/module.h>
  7. #include <linux/i2c.h>
  8. #include <linux/delay.h>
  9. #include <linux/platform_device.h>
  10. #include <linux/cdev.h>
  11. #include <linux/uaccess.h>
  12. #include <linux/fs.h>
  13. #include <asm/atomic.h>
  14. #ifdef CONFIG_COMPAT
  15. #include <linux/compat.h>
  16. #endif
  17. #include "lens_info.h"
  18. #include "lens_list.h"
  19. #define AF_DRVNAME "SUBAF"
  20. #if defined(CONFIG_MTK_LEGACY)
  21. #define I2C_CONFIG_SETTING 1
  22. #elif defined(CONFIG_OF)
  23. #define I2C_CONFIG_SETTING 2 /* device tree */
  24. #else
  25. #define I2C_CONFIG_SETTING 1
  26. #endif
  27. #if I2C_CONFIG_SETTING == 1
  28. #define LENS_I2C_BUSNUM 1
  29. #define I2C_REGISTER_ID 0x27
  30. #endif
  31. #define PLATFORM_DRIVER_NAME "lens_actuator_sub_af"
  32. #define AF_DRIVER_CLASS_NAME "actuatordrv_sub_af"
  33. #if I2C_CONFIG_SETTING == 1
  34. static struct i2c_board_info kd_lens_dev __initdata = {
  35. I2C_BOARD_INFO(AF_DRVNAME, I2C_REGISTER_ID)
  36. };
  37. #endif
  38. #define AF_DEBUG
  39. #ifdef AF_DEBUG
  40. #define LOG_INF(format, args...) pr_debug(AF_DRVNAME " [%s] " format, __func__, ##args)
  41. #else
  42. #define LOG_INF(format, args...)
  43. #endif
  44. static stAF_DrvList g_stAF_DrvList[MAX_NUM_OF_LENS] = {
  45. #ifdef CONFIG_MTK_LENS_BU6424AF_SUPPORT
  46. {1, AFDRV_BU6424AF, BU6424AF_SetI2Cclient, BU6424AF_Ioctl, BU6424AF_Release},
  47. #endif
  48. #ifdef CONFIG_MTK_LENS_BU6429AF_SUPPORT
  49. {1, AFDRV_BU6429AF, BU6429AF_SetI2Cclient, BU6429AF_Ioctl, BU6429AF_Release},
  50. #endif
  51. #ifdef CONFIG_MTK_LENS_DW9714AF_SUPPORT
  52. {1, AFDRV_DW9714AF, DW9714AF_SetI2Cclient, DW9714AF_Ioctl, DW9714AF_Release},
  53. #endif
  54. #ifdef CONFIG_MTK_LENS_DW9718AF_SUPPORT
  55. {1, AFDRV_DW9718AF, DW9718AF_SetI2Cclient, DW9718AF_Ioctl, DW9718AF_Release},
  56. #endif
  57. #ifdef CONFIG_MTK_LENS_LC898212AF_SUPPORT
  58. {1, AFDRV_LC898212AF, LC898212AF_SetI2Cclient, LC898212AF_Ioctl, LC898212AF_Release},
  59. #endif
  60. #ifdef CONFIG_MTK_LENS_FM50AF_SUPPORT
  61. {1, AFDRV_FM50AF, FM50AF_SetI2Cclient, FM50AF_Ioctl, FM50AF_Release},
  62. #endif
  63. };
  64. static stAF_DrvList *g_pstAF_CurDrv;
  65. static spinlock_t g_AF_SpinLock;
  66. static int g_s4AF_Opened;
  67. static struct i2c_client *g_pstAF_I2Cclient;
  68. static dev_t g_AF_devno;
  69. static struct cdev *g_pAF_CharDrv;
  70. static struct class *actuator_class;
  71. static long AF_SetMotorName(__user stAF_MotorName *pstMotorName)
  72. {
  73. long i4RetValue = -1;
  74. int i;
  75. stAF_MotorName stMotorName;
  76. if (copy_from_user(&stMotorName , pstMotorName, sizeof(stAF_MotorName)))
  77. LOG_INF("copy to user failed when getting motor information\n");
  78. LOG_INF("Set Motor Name : %s\n", stMotorName.uMotorName);
  79. for (i = 0; i < MAX_NUM_OF_LENS; i++) {
  80. if (g_stAF_DrvList[i].uEnable != 1)
  81. break;
  82. LOG_INF("Search Motor Name : %s\n", g_stAF_DrvList[i].uDrvName);
  83. if (strcmp(stMotorName.uMotorName, g_stAF_DrvList[i].uDrvName) == 0) {
  84. g_pstAF_CurDrv = &g_stAF_DrvList[i];
  85. g_pstAF_CurDrv->pAF_SetI2Cclient(g_pstAF_I2Cclient, &g_AF_SpinLock, &g_s4AF_Opened);
  86. i4RetValue = 1;
  87. break;
  88. }
  89. }
  90. return i4RetValue;
  91. }
  92. /* ////////////////////////////////////////////////////////////// */
  93. static long AF_Ioctl(struct file *a_pstFile, unsigned int a_u4Command, unsigned long a_u4Param)
  94. {
  95. long i4RetValue = 0;
  96. switch (a_u4Command) {
  97. case AFIOC_S_SETDRVNAME:
  98. i4RetValue = AF_SetMotorName((__user stAF_MotorName *)(a_u4Param));
  99. break;
  100. default:
  101. if (g_pstAF_CurDrv)
  102. i4RetValue = g_pstAF_CurDrv->pAF_Ioctl(a_pstFile, a_u4Command, a_u4Param);
  103. break;
  104. }
  105. return i4RetValue;
  106. }
  107. /* Main jobs: */
  108. /* 1.check for device-specified errors, device not ready. */
  109. /* 2.Initialize the device if it is opened for the first time. */
  110. /* 3.Update f_op pointer. */
  111. /* 4.Fill data structures into private_data */
  112. /* CAM_RESET */
  113. static int AF_Open(struct inode *a_pstInode, struct file *a_pstFile)
  114. {
  115. LOG_INF("Start\n");
  116. if (g_s4AF_Opened) {
  117. LOG_INF("The device is opened\n");
  118. return -EBUSY;
  119. }
  120. spin_lock(&g_AF_SpinLock);
  121. g_s4AF_Opened = 1;
  122. spin_unlock(&g_AF_SpinLock);
  123. LOG_INF("End\n");
  124. return 0;
  125. }
  126. /* Main jobs: */
  127. /* 1.Deallocate anything that "open" allocated in private_data. */
  128. /* 2.Shut down the device on last close. */
  129. /* 3.Only called once on last time. */
  130. /* Q1 : Try release multiple times. */
  131. static int AF_Release(struct inode *a_pstInode, struct file *a_pstFile)
  132. {
  133. LOG_INF("Start\n");
  134. if (g_pstAF_CurDrv) {
  135. g_pstAF_CurDrv->pAF_Release(a_pstInode, a_pstFile);
  136. g_pstAF_CurDrv = NULL;
  137. } else {
  138. spin_lock(&g_AF_SpinLock);
  139. g_s4AF_Opened = 0;
  140. spin_unlock(&g_AF_SpinLock);
  141. }
  142. LOG_INF("End\n");
  143. return 0;
  144. }
  145. static const struct file_operations g_stAF_fops = {
  146. .owner = THIS_MODULE,
  147. .open = AF_Open,
  148. .release = AF_Release,
  149. .unlocked_ioctl = AF_Ioctl,
  150. #ifdef CONFIG_COMPAT
  151. .compat_ioctl = AF_Ioctl,
  152. #endif
  153. };
  154. static inline int Register_AF_CharDrv(void)
  155. {
  156. struct device *vcm_device = NULL;
  157. LOG_INF("Start\n");
  158. /* Allocate char driver no. */
  159. if (alloc_chrdev_region(&g_AF_devno, 0, 1, AF_DRVNAME)) {
  160. LOG_INF("Allocate device no failed\n");
  161. return -EAGAIN;
  162. }
  163. /* Allocate driver */
  164. g_pAF_CharDrv = cdev_alloc();
  165. if (NULL == g_pAF_CharDrv) {
  166. unregister_chrdev_region(g_AF_devno, 1);
  167. LOG_INF("Allocate mem for kobject failed\n");
  168. return -ENOMEM;
  169. }
  170. /* Attatch file operation. */
  171. cdev_init(g_pAF_CharDrv, &g_stAF_fops);
  172. g_pAF_CharDrv->owner = THIS_MODULE;
  173. /* Add to system */
  174. if (cdev_add(g_pAF_CharDrv, g_AF_devno, 1)) {
  175. LOG_INF("Attatch file operation failed\n");
  176. unregister_chrdev_region(g_AF_devno, 1);
  177. return -EAGAIN;
  178. }
  179. actuator_class = class_create(THIS_MODULE, AF_DRIVER_CLASS_NAME);
  180. if (IS_ERR(actuator_class)) {
  181. int ret = PTR_ERR(actuator_class);
  182. LOG_INF("Unable to create class, err = %d\n", ret);
  183. return ret;
  184. }
  185. vcm_device = device_create(actuator_class, NULL, g_AF_devno, NULL, AF_DRVNAME);
  186. if (NULL == vcm_device)
  187. return -EIO;
  188. LOG_INF("End\n");
  189. return 0;
  190. }
  191. static inline void Unregister_AF_CharDrv(void)
  192. {
  193. LOG_INF("Start\n");
  194. /* Release char driver */
  195. cdev_del(g_pAF_CharDrv);
  196. unregister_chrdev_region(g_AF_devno, 1);
  197. device_destroy(actuator_class, g_AF_devno);
  198. class_destroy(actuator_class);
  199. LOG_INF("End\n");
  200. }
  201. /* //////////////////////////////////////////////////////////////////// */
  202. static int AF_i2c_probe(struct i2c_client *client, const struct i2c_device_id *id);
  203. static int AF_i2c_remove(struct i2c_client *client);
  204. static const struct i2c_device_id AF_i2c_id[] = { {AF_DRVNAME, 0}, {} };
  205. /* Compatible name must be the same with that defined in codegen.dws and cust_i2c.dtsi */
  206. /* TOOL : kernel-3.10\tools\dct */
  207. /* PATH : vendor\mediatek\proprietary\custom\#project#\kernel\dct\dct */
  208. #if I2C_CONFIG_SETTING == 2
  209. static const struct of_device_id SUBAF_of_match[] = {
  210. {.compatible = "mediatek,CAMERA_SUB_AF"},
  211. {},
  212. };
  213. #endif
  214. static struct i2c_driver AF_i2c_driver = {
  215. .probe = AF_i2c_probe,
  216. .remove = AF_i2c_remove,
  217. .driver.name = AF_DRVNAME,
  218. #if I2C_CONFIG_SETTING == 2
  219. .driver.of_match_table = SUBAF_of_match,
  220. #endif
  221. .id_table = AF_i2c_id,
  222. };
  223. static int AF_i2c_remove(struct i2c_client *client)
  224. {
  225. return 0;
  226. }
  227. /* Kirby: add new-style driver {*/
  228. static int AF_i2c_probe(struct i2c_client *client, const struct i2c_device_id *id)
  229. {
  230. int i4RetValue = 0;
  231. LOG_INF("Start\n");
  232. /* Kirby: add new-style driver { */
  233. g_pstAF_I2Cclient = client;
  234. /* Register char driver */
  235. i4RetValue = Register_AF_CharDrv();
  236. if (i4RetValue) {
  237. LOG_INF(" register char device failed!\n");
  238. return i4RetValue;
  239. }
  240. spin_lock_init(&g_AF_SpinLock);
  241. LOG_INF("Attached!!\n");
  242. return 0;
  243. }
  244. static int AF_probe(struct platform_device *pdev)
  245. {
  246. return i2c_add_driver(&AF_i2c_driver);
  247. }
  248. static int AF_remove(struct platform_device *pdev)
  249. {
  250. i2c_del_driver(&AF_i2c_driver);
  251. return 0;
  252. }
  253. static int AF_suspend(struct platform_device *pdev, pm_message_t mesg)
  254. {
  255. return 0;
  256. }
  257. static int AF_resume(struct platform_device *pdev)
  258. {
  259. return 0;
  260. }
  261. /* platform structure */
  262. static struct platform_driver g_stAF_Driver = {
  263. .probe = AF_probe,
  264. .remove = AF_remove,
  265. .suspend = AF_suspend,
  266. .resume = AF_resume,
  267. .driver = {
  268. .name = PLATFORM_DRIVER_NAME,
  269. .owner = THIS_MODULE,
  270. }
  271. };
  272. static struct platform_device g_stAF_device = {
  273. .name = PLATFORM_DRIVER_NAME,
  274. .id = 0,
  275. .dev = {}
  276. };
  277. static int __init SUBAF_i2C_init(void)
  278. {
  279. #if I2C_CONFIG_SETTING == 1
  280. i2c_register_board_info(LENS_I2C_BUSNUM, &kd_lens_dev, 1);
  281. #endif
  282. if (platform_device_register(&g_stAF_device)) {
  283. LOG_INF("failed to register AF driver\n");
  284. return -ENODEV;
  285. }
  286. if (platform_driver_register(&g_stAF_Driver)) {
  287. LOG_INF("Failed to register AF driver\n");
  288. return -ENODEV;
  289. }
  290. return 0;
  291. }
  292. static void __exit SUBAF_i2C_exit(void)
  293. {
  294. platform_driver_unregister(&g_stAF_Driver);
  295. }
  296. module_init(SUBAF_i2C_init);
  297. module_exit(SUBAF_i2C_exit);
  298. MODULE_DESCRIPTION("SUBAF lens module driver");
  299. MODULE_AUTHOR("KY Chen <ky.chen@Mediatek.com>");
  300. MODULE_LICENSE("GPL");