ms.c 10 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334
  1. /*****************************************************************
  2. ** **
  3. ** Copyright (C) 2004 Amlogic,Inc. **
  4. ** All rights reserved **
  5. ** Filename : sd.c /Project:AVOS driver **
  6. ** Revision : 1.0 **
  7. ** **
  8. *****************************************************************/
  9. #include <linux/slab.h>
  10. #include <linux/dma-mapping.h>
  11. #include <linux/pagemap.h>
  12. #include <linux/fs.h>
  13. #include <linux/cardreader/card_block.h>
  14. #include <linux/cardreader/cardreader.h>
  15. #include "ms_misc.h"
  16. extern unsigned ms_force_write_two_times;
  17. static unsigned ms_backup_input_val = 0;
  18. static unsigned ms_backup_output_val = 0;
  19. static unsigned MS_BAKUP_INPUT_REG = (unsigned)&ms_backup_input_val;
  20. static unsigned MS_BAKUP_OUTPUT_REG = (unsigned)&ms_backup_output_val;
  21. unsigned MS_BS_OUTPUT_EN_REG;
  22. unsigned MS_BS_OUTPUT_EN_MASK;
  23. unsigned MS_BS_OUTPUT_REG;
  24. unsigned MS_BS_OUTPUT_MASK;
  25. unsigned MS_CLK_OUTPUT_EN_REG;
  26. unsigned MS_CLK_OUTPUT_EN_MASK;
  27. unsigned MS_CLK_OUTPUT_REG;
  28. unsigned MS_CLK_OUTPUT_MASK;
  29. unsigned MS_DAT_OUTPUT_EN_REG;
  30. unsigned MS_DAT0_OUTPUT_EN_MASK;
  31. unsigned MS_DAT0_3_OUTPUT_EN_MASK;
  32. unsigned MS_DAT_INPUT_REG;
  33. unsigned MS_DAT_OUTPUT_REG;
  34. unsigned MS_DAT0_INPUT_MASK;
  35. unsigned MS_DAT0_OUTPUT_MASK;
  36. unsigned MS_DAT0_3_INPUT_MASK;
  37. unsigned MS_DAT0_3_OUTPUT_MASK;
  38. unsigned MS_DAT_INPUT_OFFSET;
  39. unsigned MS_DAT_OUTPUT_OFFSET;
  40. unsigned MS_INS_OUTPUT_EN_REG;
  41. unsigned MS_INS_OUTPUT_EN_MASK;
  42. unsigned MS_INS_INPUT_REG;
  43. unsigned MS_INS_INPUT_MASK;
  44. unsigned MS_PWR_OUTPUT_EN_REG;
  45. unsigned MS_PWR_OUTPUT_EN_MASK;
  46. unsigned MS_PWR_OUTPUT_REG;
  47. unsigned MS_PWR_OUTPUT_MASK;
  48. unsigned MS_PWR_EN_LEVEL;
  49. unsigned MS_WORK_MODE;
  50. void ms_insert_detector(struct memory_card *card)
  51. {
  52. MS_MSPRO_Card_Info_t *ms_mspro_info = (MS_MSPRO_Card_Info_t *)card->card_info;
  53. int ret = ms_mspro_check_insert(ms_mspro_info);
  54. if(ret)
  55. card->card_status = CARD_INSERTED;
  56. else
  57. card->card_status = CARD_REMOVED;
  58. return;
  59. }
  60. extern unsigned char disable_port_switch;
  61. void ms_open(struct memory_card *card)
  62. {
  63. int ret;
  64. MS_MSPRO_Card_Info_t *ms_mspro_info = (MS_MSPRO_Card_Info_t *)card->card_info;
  65. ret = ms_mspro_init(ms_mspro_info);
  66. if(ret)
  67. {
  68. disable_port_switch = 1;
  69. ret = ms_mspro_init(ms_mspro_info);
  70. }
  71. disable_port_switch = 0;
  72. card->capacity = ms_mspro_info->blk_nums;
  73. if(ret)
  74. card->unit_state = CARD_UNIT_READY;
  75. else
  76. card->unit_state = CARD_UNIT_PROCESSED;
  77. return;
  78. }
  79. void ms_close(struct memory_card *card)
  80. {
  81. MS_MSPRO_Card_Info_t *ms_mspro_info = (MS_MSPRO_Card_Info_t *)card->card_info;
  82. if (ms_mspro_info->data_buf != NULL)
  83. {
  84. dma_free_coherent(NULL, 4096, ms_mspro_info->data_buf, (dma_addr_t )ms_mspro_info->data_phy_buf);
  85. ms_mspro_info->data_buf = NULL;
  86. ms_mspro_info->data_phy_buf = NULL;
  87. }
  88. if (ms_mspro_info->ms_mspro_buf != NULL)
  89. {
  90. dma_free_coherent(NULL, 4096, ms_mspro_info->ms_mspro_buf, (dma_addr_t )ms_mspro_info->ms_mspro_phy_buf);
  91. ms_mspro_info->ms_mspro_buf = NULL;
  92. ms_mspro_info->ms_mspro_phy_buf = NULL;
  93. }
  94. ms_mspro_exit(ms_mspro_info);
  95. ms_mspro_free(ms_mspro_info);
  96. ms_mspro_info = NULL;
  97. card->card_info = NULL;
  98. card->unit_state = CARD_UNIT_PROCESSED;
  99. return;
  100. }
  101. unsigned char ms_read_info(struct memory_card *card, u32 *blk_length, u32 *capacity, u32 *raw_cid)
  102. {
  103. MS_MSPRO_Card_Info_t *ms_mspro_info = (MS_MSPRO_Card_Info_t *)card->card_info;
  104. if(ms_mspro_info->inited_flag)
  105. {
  106. if(blk_length)
  107. *blk_length = 512;
  108. if(capacity)
  109. *capacity = ms_mspro_info->blk_nums;
  110. if(raw_cid)
  111. memcpy(raw_cid, &(ms_mspro_info->raw_cid), sizeof(ms_mspro_info->raw_cid));
  112. return 0;
  113. }
  114. else
  115. return 1;
  116. }
  117. static void ms_io_init(struct memory_card *card)
  118. {
  119. struct aml_card_info *aml_card_info = card->card_plat_info;
  120. MS_WORK_MODE = aml_card_info->work_mode;
  121. switch (aml_card_info->io_pad_type) {
  122. case SDIO_GPIOA_0_5:
  123. MS_BS_OUTPUT_EN_REG = EGPIO_GPIOA_ENABLE;
  124. MS_BS_OUTPUT_EN_MASK = PREG_IO_9_MASK;
  125. MS_BS_OUTPUT_REG = EGPIO_GPIOA_OUTPUT;
  126. MS_BS_OUTPUT_MASK = PREG_IO_9_MASK;
  127. MS_CLK_OUTPUT_EN_REG = EGPIO_GPIOA_ENABLE;
  128. MS_CLK_OUTPUT_EN_MASK = PREG_IO_8_MASK;
  129. MS_CLK_OUTPUT_REG = EGPIO_GPIOA_OUTPUT;
  130. MS_CLK_OUTPUT_MASK = PREG_IO_8_MASK;
  131. MS_DAT_OUTPUT_EN_REG = EGPIO_GPIOA_ENABLE;
  132. MS_DAT0_OUTPUT_EN_MASK = PREG_IO_4_MASK;
  133. MS_DAT0_3_OUTPUT_EN_MASK = PREG_IO_4_7_MASK;
  134. MS_DAT_INPUT_REG = EGPIO_GPIOA_INPUT;
  135. MS_DAT_OUTPUT_REG = EGPIO_GPIOA_OUTPUT;
  136. MS_DAT0_INPUT_MASK = PREG_IO_4_MASK;
  137. MS_DAT0_OUTPUT_MASK = PREG_IO_4_MASK;
  138. MS_DAT0_3_INPUT_MASK = PREG_IO_4_7_MASK;
  139. MS_DAT0_3_OUTPUT_MASK = PREG_IO_4_7_MASK;
  140. MS_DAT_INPUT_OFFSET = 4;
  141. MS_DAT_OUTPUT_OFFSET = 4;
  142. break;
  143. case SDIO_GPIOA_9_14:
  144. MS_BS_OUTPUT_EN_REG = EGPIO_GPIOA_ENABLE;
  145. MS_BS_OUTPUT_EN_MASK = PREG_IO_18_MASK;
  146. MS_BS_OUTPUT_REG = EGPIO_GPIOA_OUTPUT;
  147. MS_BS_OUTPUT_MASK = PREG_IO_18_MASK;
  148. MS_CLK_OUTPUT_EN_REG = EGPIO_GPIOA_ENABLE;
  149. MS_CLK_OUTPUT_EN_MASK = PREG_IO_17_MASK;
  150. MS_CLK_OUTPUT_REG = EGPIO_GPIOA_OUTPUT;
  151. MS_CLK_OUTPUT_MASK = PREG_IO_17_MASK;
  152. MS_DAT_OUTPUT_EN_REG = EGPIO_GPIOA_ENABLE;
  153. MS_DAT0_OUTPUT_EN_MASK = PREG_IO_13_MASK;
  154. MS_DAT0_3_OUTPUT_EN_MASK = PREG_IO_13_16_MASK;
  155. MS_DAT_INPUT_REG = EGPIO_GPIOA_INPUT;
  156. MS_DAT_OUTPUT_REG = EGPIO_GPIOA_OUTPUT;
  157. MS_DAT0_INPUT_MASK = PREG_IO_13_MASK;
  158. MS_DAT0_OUTPUT_MASK = PREG_IO_13_MASK;
  159. MS_DAT0_3_INPUT_MASK = PREG_IO_13_16_MASK;
  160. MS_DAT0_3_OUTPUT_MASK = PREG_IO_13_16_MASK;
  161. MS_DAT_INPUT_OFFSET = 13;
  162. MS_DAT_OUTPUT_OFFSET = 13;
  163. break;
  164. case SDIO_GPIOB_2_7:
  165. MS_BS_OUTPUT_EN_REG = EGPIO_GPIOA_ENABLE;
  166. MS_BS_OUTPUT_EN_MASK = PREG_IO_21_MASK;
  167. MS_BS_OUTPUT_REG = EGPIO_GPIOA_OUTPUT;
  168. MS_BS_OUTPUT_MASK = PREG_IO_21_MASK;
  169. MS_CLK_OUTPUT_EN_REG = EGPIO_GPIOA_ENABLE;
  170. MS_CLK_OUTPUT_EN_MASK = PREG_IO_22_MASK;
  171. MS_CLK_OUTPUT_REG = EGPIO_GPIOA_OUTPUT;
  172. MS_CLK_OUTPUT_MASK = PREG_IO_22_MASK;
  173. MS_DAT_OUTPUT_EN_REG = EGPIO_GPIOA_ENABLE;
  174. MS_DAT0_OUTPUT_EN_MASK = PREG_IO_23_MASK;
  175. MS_DAT0_3_OUTPUT_EN_MASK = PREG_IO_23_26_MASK;
  176. MS_DAT_INPUT_REG = EGPIO_GPIOA_INPUT;
  177. MS_DAT_OUTPUT_REG = EGPIO_GPIOA_OUTPUT;
  178. MS_DAT0_INPUT_MASK = PREG_IO_23_MASK;
  179. MS_DAT0_OUTPUT_MASK = PREG_IO_23_MASK;
  180. MS_DAT0_3_INPUT_MASK = PREG_IO_23_26_MASK;
  181. MS_DAT0_3_OUTPUT_MASK = PREG_IO_23_26_MASK;
  182. MS_DAT_INPUT_OFFSET = 23;
  183. MS_DAT_OUTPUT_OFFSET = 23;
  184. break;
  185. case SDIO_GPIOE_6_11:
  186. MS_BS_OUTPUT_EN_REG = EGPIO_GPIOE_ENABLE;
  187. MS_BS_OUTPUT_EN_MASK = PREG_IO_7_MASK;
  188. MS_BS_OUTPUT_REG = EGPIO_GPIOE_OUTPUT;
  189. MS_BS_OUTPUT_MASK = PREG_IO_7_MASK;
  190. MS_CLK_OUTPUT_EN_REG = EGPIO_GPIOE_ENABLE;
  191. MS_CLK_OUTPUT_EN_MASK = PREG_IO_6_MASK;
  192. MS_CLK_OUTPUT_REG = EGPIO_GPIOE_OUTPUT;
  193. MS_CLK_OUTPUT_MASK = PREG_IO_6_MASK;
  194. MS_DAT_OUTPUT_EN_REG = EGPIO_GPIOE_ENABLE;
  195. MS_DAT0_OUTPUT_EN_MASK = PREG_IO_8_MASK;
  196. MS_DAT0_3_OUTPUT_EN_MASK = PREG_IO_8_11_MASK;
  197. MS_DAT_INPUT_REG = EGPIO_GPIOE_INPUT;
  198. MS_DAT_OUTPUT_REG = EGPIO_GPIOE_OUTPUT;
  199. MS_DAT0_INPUT_MASK = PREG_IO_8_MASK;
  200. MS_DAT0_OUTPUT_MASK = PREG_IO_8_MASK;
  201. MS_DAT0_3_INPUT_MASK = PREG_IO_8_11_MASK;
  202. MS_DAT0_3_OUTPUT_MASK = PREG_IO_8_11_MASK;
  203. MS_DAT_INPUT_OFFSET = 8;
  204. MS_DAT_OUTPUT_OFFSET = 8;
  205. break;
  206. default:
  207. printk("Warning couldn`t find any valid hw io pad!!!\n");
  208. break;
  209. }
  210. if (aml_card_info->card_ins_en_reg) {
  211. MS_INS_OUTPUT_EN_REG = aml_card_info->card_ins_en_reg;
  212. MS_INS_OUTPUT_EN_MASK = aml_card_info->card_ins_en_mask;
  213. MS_INS_INPUT_REG = aml_card_info->card_ins_input_reg;
  214. MS_INS_INPUT_MASK = aml_card_info->card_ins_input_mask;
  215. }
  216. else {
  217. MS_INS_OUTPUT_EN_REG = MS_BAKUP_OUTPUT_REG;
  218. MS_INS_OUTPUT_EN_MASK = 1;
  219. MS_INS_INPUT_REG = MS_BAKUP_INPUT_REG;
  220. MS_INS_INPUT_MASK = 1;
  221. }
  222. if (aml_card_info->card_power_en_reg) {
  223. MS_PWR_OUTPUT_EN_REG = aml_card_info->card_power_en_reg;
  224. MS_PWR_OUTPUT_EN_MASK = aml_card_info->card_power_en_mask;
  225. MS_PWR_OUTPUT_REG = aml_card_info->card_power_output_reg;
  226. MS_PWR_OUTPUT_MASK = aml_card_info->card_power_output_mask;
  227. MS_PWR_EN_LEVEL = aml_card_info->card_power_en_lev;
  228. }
  229. else {
  230. MS_PWR_OUTPUT_EN_REG = MS_BAKUP_OUTPUT_REG;
  231. MS_PWR_OUTPUT_EN_MASK = 1;
  232. MS_PWR_OUTPUT_REG = MS_BAKUP_OUTPUT_REG;
  233. MS_PWR_OUTPUT_MASK = 1;
  234. MS_PWR_EN_LEVEL = 0;
  235. }
  236. return;
  237. }
  238. static int ms_request(struct memory_card *card, struct card_blk_request *brq)
  239. {
  240. MS_MSPRO_Card_Info_t *ms_info = (MS_MSPRO_Card_Info_t *)card->card_info;
  241. unsigned int lba, byte_cnt;
  242. unsigned char *data_buf;
  243. lba = brq->card_data.lba;
  244. byte_cnt = brq->card_data.blk_size * brq->card_data.blk_nums;
  245. data_buf = brq->crq.buf;
  246. if(brq->crq.cmd == READ) {
  247. //printk("R(%d,%d)\n", lba, byte_cnt);
  248. brq->card_data.error = ms_mspro_read_data(ms_info, lba, byte_cnt, data_buf);
  249. }
  250. else if(brq->crq.cmd == WRITE) {
  251. //printk("W(%d,%d)\n", lba, byte_cnt);
  252. brq->card_data.error = ms_mspro_write_data(ms_info, lba, byte_cnt, data_buf);
  253. }
  254. return 0;
  255. }
  256. int ms_probe(struct memory_card *card)
  257. {
  258. struct aml_card_info *aml_card_info = card->card_plat_info;
  259. MS_MSPRO_Card_Info_t *ms_mspro_info = ms_mspro_malloc(sizeof(MS_MSPRO_Card_Info_t), GFP_KERNEL);
  260. if (ms_mspro_info == NULL)
  261. return -ENOMEM;
  262. if (card->host->dma_buf != NULL) {
  263. ms_mspro_info->dma_buf = card->host->dma_buf;
  264. ms_mspro_info->dma_phy_buf = card->host->dma_phy_buf;
  265. }
  266. card->card_info = ms_mspro_info;
  267. card->card_io_init = ms_io_init;
  268. card->card_detector = ms_insert_detector;
  269. card->card_insert_process = ms_open;
  270. card->card_remove_process = ms_close;
  271. card->card_request_process = ms_request;
  272. if (aml_card_info->card_extern_init)
  273. aml_card_info->card_extern_init();
  274. card->card_io_init(card);
  275. ms_mspro_info->io_pad_type = aml_card_info->io_pad_type;
  276. ms_mspro_prepare_init(ms_mspro_info);
  277. ms_mspro_info->data_buf = dma_alloc_coherent(NULL, PAGE_CACHE_SIZE, (dma_addr_t *)&ms_mspro_info->data_phy_buf, GFP_KERNEL);
  278. if(ms_mspro_info->data_buf == NULL)
  279. return -ENOMEM;
  280. ms_mspro_info->ms_mspro_buf = dma_alloc_coherent(NULL, PAGE_CACHE_SIZE, (dma_addr_t *)&ms_mspro_info->ms_mspro_phy_buf, GFP_KERNEL);
  281. if(ms_mspro_info->ms_mspro_buf == NULL)
  282. return -ENOMEM;
  283. return 0;
  284. }