s5p_mmc.c 11 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477
  1. /*
  2. * (C) Copyright 2009 SAMSUNG Electronics
  3. * Minkyu Kang <mk7.kang@samsung.com>
  4. * Jaehoon Chung <jh80.chung@samsung.com>
  5. *
  6. * This program is free software; you can redistribute it and/or modify
  7. * it under the terms of the GNU General Public License as published by
  8. * the Free Software Foundation; either version 2 of the License, or
  9. * (at your option) any later version.
  10. *
  11. * This program is distributed in the hope that it will be useful,
  12. * but WITHOUT ANY WARRANTY; without even the implied warranty of
  13. * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  14. * GNU General Public License for more details.
  15. *
  16. * You should have received a copy of the GNU General Public License
  17. * along with this program; if not, write to the Free Software
  18. * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
  19. */
  20. #include <common.h>
  21. #include <mmc.h>
  22. #include <asm/io.h>
  23. #include <asm/arch/mmc.h>
  24. /* support 4 mmc hosts */
  25. struct mmc mmc_dev[4];
  26. struct mmc_host mmc_host[4];
  27. static inline struct s5p_mmc *s5p_get_base_mmc(int dev_index)
  28. {
  29. unsigned long offset = dev_index * sizeof(struct s5p_mmc);
  30. return (struct s5p_mmc *)(samsung_get_base_mmc() + offset);
  31. }
  32. static void mmc_prepare_data(struct mmc_host *host, struct mmc_data *data)
  33. {
  34. unsigned char ctrl;
  35. debug("data->dest: %08x\n", (u32)data->dest);
  36. writel((u32)data->dest, &host->reg->sysad);
  37. /*
  38. * DMASEL[4:3]
  39. * 00 = Selects SDMA
  40. * 01 = Reserved
  41. * 10 = Selects 32-bit Address ADMA2
  42. * 11 = Selects 64-bit Address ADMA2
  43. */
  44. ctrl = readb(&host->reg->hostctl);
  45. ctrl &= ~(3 << 3);
  46. writeb(ctrl, &host->reg->hostctl);
  47. /* We do not handle DMA boundaries, so set it to max (512 KiB) */
  48. writew((7 << 12) | (data->blocksize & 0xFFF), &host->reg->blksize);
  49. writew(data->blocks, &host->reg->blkcnt);
  50. }
  51. static void mmc_set_transfer_mode(struct mmc_host *host, struct mmc_data *data)
  52. {
  53. unsigned short mode;
  54. /*
  55. * TRNMOD
  56. * MUL1SIN0[5] : Multi/Single Block Select
  57. * RD1WT0[4] : Data Transfer Direction Select
  58. * 1 = read
  59. * 0 = write
  60. * ENACMD12[2] : Auto CMD12 Enable
  61. * ENBLKCNT[1] : Block Count Enable
  62. * ENDMA[0] : DMA Enable
  63. */
  64. mode = (1 << 1) | (1 << 0);
  65. if (data->blocks > 1)
  66. mode |= (1 << 5);
  67. if (data->flags & MMC_DATA_READ)
  68. mode |= (1 << 4);
  69. writew(mode, &host->reg->trnmod);
  70. }
  71. static int mmc_send_cmd(struct mmc *mmc, struct mmc_cmd *cmd,
  72. struct mmc_data *data)
  73. {
  74. struct mmc_host *host = (struct mmc_host *)mmc->priv;
  75. int flags, i;
  76. unsigned int timeout;
  77. unsigned int mask;
  78. unsigned int retry = 0x100000;
  79. /* Wait max 10 ms */
  80. timeout = 10;
  81. /*
  82. * PRNSTS
  83. * CMDINHDAT[1] : Command Inhibit (DAT)
  84. * CMDINHCMD[0] : Command Inhibit (CMD)
  85. */
  86. mask = (1 << 0);
  87. if ((data != NULL) || (cmd->resp_type & MMC_RSP_BUSY))
  88. mask |= (1 << 1);
  89. /*
  90. * We shouldn't wait for data inihibit for stop commands, even
  91. * though they might use busy signaling
  92. */
  93. if (data)
  94. mask &= ~(1 << 1);
  95. while (readl(&host->reg->prnsts) & mask) {
  96. if (timeout == 0) {
  97. printf("%s: timeout error\n", __func__);
  98. return -1;
  99. }
  100. timeout--;
  101. udelay(1000);
  102. }
  103. if (data)
  104. mmc_prepare_data(host, data);
  105. debug("cmd->arg: %08x\n", cmd->cmdarg);
  106. writel(cmd->cmdarg, &host->reg->argument);
  107. if (data)
  108. mmc_set_transfer_mode(host, data);
  109. if ((cmd->resp_type & MMC_RSP_136) && (cmd->resp_type & MMC_RSP_BUSY))
  110. return -1;
  111. /*
  112. * CMDREG
  113. * CMDIDX[13:8] : Command index
  114. * DATAPRNT[5] : Data Present Select
  115. * ENCMDIDX[4] : Command Index Check Enable
  116. * ENCMDCRC[3] : Command CRC Check Enable
  117. * RSPTYP[1:0]
  118. * 00 = No Response
  119. * 01 = Length 136
  120. * 10 = Length 48
  121. * 11 = Length 48 Check busy after response
  122. */
  123. if (!(cmd->resp_type & MMC_RSP_PRESENT))
  124. flags = 0;
  125. else if (cmd->resp_type & MMC_RSP_136)
  126. flags = (1 << 0);
  127. else if (cmd->resp_type & MMC_RSP_BUSY)
  128. flags = (3 << 0);
  129. else
  130. flags = (2 << 0);
  131. if (cmd->resp_type & MMC_RSP_CRC)
  132. flags |= (1 << 3);
  133. if (cmd->resp_type & MMC_RSP_OPCODE)
  134. flags |= (1 << 4);
  135. if (data)
  136. flags |= (1 << 5);
  137. debug("cmd: %d\n", cmd->cmdidx);
  138. writew((cmd->cmdidx << 8) | flags, &host->reg->cmdreg);
  139. for (i = 0; i < retry; i++) {
  140. mask = readl(&host->reg->norintsts);
  141. /* Command Complete */
  142. if (mask & (1 << 0)) {
  143. if (!data)
  144. writel(mask, &host->reg->norintsts);
  145. break;
  146. }
  147. }
  148. if (i == retry) {
  149. printf("%s: waiting for status update\n", __func__);
  150. return TIMEOUT;
  151. }
  152. if (mask & (1 << 16)) {
  153. /* Timeout Error */
  154. debug("timeout: %08x cmd %d\n", mask, cmd->cmdidx);
  155. return TIMEOUT;
  156. } else if (mask & (1 << 15)) {
  157. /* Error Interrupt */
  158. debug("error: %08x cmd %d\n", mask, cmd->cmdidx);
  159. return -1;
  160. }
  161. if (cmd->resp_type & MMC_RSP_PRESENT) {
  162. if (cmd->resp_type & MMC_RSP_136) {
  163. /* CRC is stripped so we need to do some shifting. */
  164. for (i = 0; i < 4; i++) {
  165. unsigned int offset =
  166. (unsigned int)(&host->reg->rspreg3 - i);
  167. cmd->response[i] = readl(offset) << 8;
  168. if (i != 3) {
  169. cmd->response[i] |=
  170. readb(offset - 1);
  171. }
  172. debug("cmd->resp[%d]: %08x\n",
  173. i, cmd->response[i]);
  174. }
  175. } else if (cmd->resp_type & MMC_RSP_BUSY) {
  176. for (i = 0; i < retry; i++) {
  177. /* PRNTDATA[23:20] : DAT[3:0] Line Signal */
  178. if (readl(&host->reg->prnsts)
  179. & (1 << 20)) /* DAT[0] */
  180. break;
  181. }
  182. if (i == retry) {
  183. printf("%s: card is still busy\n", __func__);
  184. return TIMEOUT;
  185. }
  186. cmd->response[0] = readl(&host->reg->rspreg0);
  187. debug("cmd->resp[0]: %08x\n", cmd->response[0]);
  188. } else {
  189. cmd->response[0] = readl(&host->reg->rspreg0);
  190. debug("cmd->resp[0]: %08x\n", cmd->response[0]);
  191. }
  192. }
  193. if (data) {
  194. while (1) {
  195. mask = readl(&host->reg->norintsts);
  196. if (mask & (1 << 15)) {
  197. /* Error Interrupt */
  198. writel(mask, &host->reg->norintsts);
  199. printf("%s: error during transfer: 0x%08x\n",
  200. __func__, mask);
  201. return -1;
  202. } else if (mask & (1 << 3)) {
  203. /* DMA Interrupt */
  204. debug("DMA end\n");
  205. break;
  206. } else if (mask & (1 << 1)) {
  207. /* Transfer Complete */
  208. debug("r/w is done\n");
  209. break;
  210. }
  211. }
  212. writel(mask, &host->reg->norintsts);
  213. }
  214. udelay(1000);
  215. return 0;
  216. }
  217. static void mmc_change_clock(struct mmc_host *host, uint clock)
  218. {
  219. int div;
  220. unsigned short clk;
  221. unsigned long timeout;
  222. unsigned long ctrl2;
  223. /*
  224. * SELBASECLK[5:4]
  225. * 00/01 = HCLK
  226. * 10 = EPLL
  227. * 11 = XTI or XEXTCLK
  228. */
  229. ctrl2 = readl(&host->reg->control2);
  230. ctrl2 &= ~(3 << 4);
  231. ctrl2 |= (2 << 4);
  232. writel(ctrl2, &host->reg->control2);
  233. writew(0, &host->reg->clkcon);
  234. /* XXX: we assume that clock is between 40MHz and 50MHz */
  235. if (clock == 0)
  236. goto out;
  237. else if (clock <= 400000)
  238. div = 0x100;
  239. else if (clock <= 20000000)
  240. div = 4;
  241. else if (clock <= 26000000)
  242. div = 2;
  243. else
  244. div = 1;
  245. debug("div: %d\n", div);
  246. div >>= 1;
  247. /*
  248. * CLKCON
  249. * SELFREQ[15:8] : base clock divied by value
  250. * ENSDCLK[2] : SD Clock Enable
  251. * STBLINTCLK[1] : Internal Clock Stable
  252. * ENINTCLK[0] : Internal Clock Enable
  253. */
  254. clk = (div << 8) | (1 << 0);
  255. writew(clk, &host->reg->clkcon);
  256. /* Wait max 10 ms */
  257. timeout = 10;
  258. while (!(readw(&host->reg->clkcon) & (1 << 1))) {
  259. if (timeout == 0) {
  260. printf("%s: timeout error\n", __func__);
  261. return;
  262. }
  263. timeout--;
  264. udelay(1000);
  265. }
  266. clk |= (1 << 2);
  267. writew(clk, &host->reg->clkcon);
  268. out:
  269. host->clock = clock;
  270. }
  271. static void mmc_set_ios(struct mmc *mmc)
  272. {
  273. struct mmc_host *host = mmc->priv;
  274. unsigned char ctrl;
  275. unsigned long val;
  276. debug("bus_width: %x, clock: %d\n", mmc->bus_width, mmc->clock);
  277. /*
  278. * SELCLKPADDS[17:16]
  279. * 00 = 2mA
  280. * 01 = 4mA
  281. * 10 = 7mA
  282. * 11 = 9mA
  283. */
  284. writel(0x3 << 16, &host->reg->control4);
  285. val = readl(&host->reg->control2);
  286. val &= (0x3 << 4);
  287. val |= (1 << 31) | /* write status clear async mode enable */
  288. (1 << 30) | /* command conflict mask enable */
  289. (1 << 14) | /* Feedback Clock Enable for Rx Clock */
  290. (1 << 8); /* SDCLK hold enable */
  291. writel(val, &host->reg->control2);
  292. /*
  293. * FCSEL1[15] FCSEL0[7]
  294. * FCSel[1:0] : Rx Feedback Clock Delay Control
  295. * Inverter delay means10ns delay if SDCLK 50MHz setting
  296. * 01 = Delay1 (basic delay)
  297. * 11 = Delay2 (basic delay + 2ns)
  298. * 00 = Delay3 (inverter delay)
  299. * 10 = Delay4 (inverter delay + 2ns)
  300. */
  301. writel(0x8080, &host->reg->control3);
  302. mmc_change_clock(host, mmc->clock);
  303. ctrl = readb(&host->reg->hostctl);
  304. /*
  305. * WIDE8[5]
  306. * 0 = Depend on WIDE4
  307. * 1 = 8-bit mode
  308. * WIDE4[1]
  309. * 1 = 4-bit mode
  310. * 0 = 1-bit mode
  311. */
  312. if (mmc->bus_width == 8)
  313. ctrl |= (1 << 5);
  314. else if (mmc->bus_width == 4)
  315. ctrl |= (1 << 1);
  316. else
  317. ctrl &= ~(1 << 1);
  318. /*
  319. * OUTEDGEINV[2]
  320. * 1 = Riging edge output
  321. * 0 = Falling edge output
  322. */
  323. ctrl &= ~(1 << 2);
  324. writeb(ctrl, &host->reg->hostctl);
  325. }
  326. static void mmc_reset(struct mmc_host *host)
  327. {
  328. unsigned int timeout;
  329. /*
  330. * RSTALL[0] : Software reset for all
  331. * 1 = reset
  332. * 0 = work
  333. */
  334. writeb((1 << 0), &host->reg->swrst);
  335. host->clock = 0;
  336. /* Wait max 100 ms */
  337. timeout = 100;
  338. /* hw clears the bit when it's done */
  339. while (readb(&host->reg->swrst) & (1 << 0)) {
  340. if (timeout == 0) {
  341. printf("%s: timeout error\n", __func__);
  342. return;
  343. }
  344. timeout--;
  345. udelay(1000);
  346. }
  347. }
  348. static int mmc_core_init(struct mmc *mmc)
  349. {
  350. struct mmc_host *host = (struct mmc_host *)mmc->priv;
  351. unsigned int mask;
  352. mmc_reset(host);
  353. host->version = readw(&host->reg->hcver);
  354. /* mask all */
  355. writel(0xffffffff, &host->reg->norintstsen);
  356. writel(0xffffffff, &host->reg->norintsigen);
  357. writeb(0xe, &host->reg->timeoutcon); /* TMCLK * 2^27 */
  358. /*
  359. * NORMAL Interrupt Status Enable Register init
  360. * [5] ENSTABUFRDRDY : Buffer Read Ready Status Enable
  361. * [4] ENSTABUFWTRDY : Buffer write Ready Status Enable
  362. * [1] ENSTASTANSCMPLT : Transfre Complete Status Enable
  363. * [0] ENSTACMDCMPLT : Command Complete Status Enable
  364. */
  365. mask = readl(&host->reg->norintstsen);
  366. mask &= ~(0xffff);
  367. mask |= (1 << 5) | (1 << 4) | (1 << 1) | (1 << 0);
  368. writel(mask, &host->reg->norintstsen);
  369. /*
  370. * NORMAL Interrupt Signal Enable Register init
  371. * [1] ENSTACMDCMPLT : Transfer Complete Signal Enable
  372. */
  373. mask = readl(&host->reg->norintsigen);
  374. mask &= ~(0xffff);
  375. mask |= (1 << 1);
  376. writel(mask, &host->reg->norintsigen);
  377. return 0;
  378. }
  379. static int s5p_mmc_initialize(int dev_index, int bus_width)
  380. {
  381. struct mmc *mmc;
  382. mmc = &mmc_dev[dev_index];
  383. sprintf(mmc->name, "SAMSUNG SD/MMC");
  384. mmc->priv = &mmc_host[dev_index];
  385. mmc->send_cmd = mmc_send_cmd;
  386. mmc->set_ios = mmc_set_ios;
  387. mmc->init = mmc_core_init;
  388. mmc->voltages = MMC_VDD_32_33 | MMC_VDD_33_34 | MMC_VDD_165_195;
  389. if (bus_width == 8)
  390. mmc->host_caps = MMC_MODE_8BIT;
  391. else
  392. mmc->host_caps = MMC_MODE_4BIT;
  393. mmc->host_caps |= MMC_MODE_HS_52MHz | MMC_MODE_HS;
  394. mmc->f_min = 400000;
  395. mmc->f_max = 52000000;
  396. mmc_host[dev_index].clock = 0;
  397. mmc_host[dev_index].reg = s5p_get_base_mmc(dev_index);
  398. mmc_register(mmc);
  399. return 0;
  400. }
  401. int s5p_mmc_init(int dev_index, int bus_width)
  402. {
  403. return s5p_mmc_initialize(dev_index, bus_width);
  404. }