MMCHS.c 40 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798991001011021031041051061071081091101111121131141151161171181191201211221231241251261271281291301311321331341351361371381391401411421431441451461471481491501511521531541551561571581591601611621631641651661671681691701711721731741751761771781791801811821831841851861871881891901911921931941951961971981992002012022032042052062072082092102112122132142152162172182192202212222232242252262272282292302312322332342352362372382392402412422432442452462472482492502512522532542552562572582592602612622632642652662672682692702712722732742752762772782792802812822832842852862872882892902912922932942952962972982993003013023033043053063073083093103113123133143153163173183193203213223233243253263273283293303313323333343353363373383393403413423433443453463473483493503513523533543553563573583593603613623633643653663673683693703713723733743753763773783793803813823833843853863873883893903913923933943953963973983994004014024034044054064074084094104114124134144154164174184194204214224234244254264274284294304314324334344354364374384394404414424434444454464474484494504514524534544554564574584594604614624634644654664674684694704714724734744754764774784794804814824834844854864874884894904914924934944954964974984995005015025035045055065075085095105115125135145155165175185195205215225235245255265275285295305315325335345355365375385395405415425435445455465475485495505515525535545555565575585595605615625635645655665675685695705715725735745755765775785795805815825835845855865875885895905915925935945955965975985996006016026036046056066076086096106116126136146156166176186196206216226236246256266276286296306316326336346356366376386396406416426436446456466476486496506516526536546556566576586596606616626636646656666676686696706716726736746756766776786796806816826836846856866876886896906916926936946956966976986997007017027037047057067077087097107117127137147157167177187197207217227237247257267277287297307317327337347357367377387397407417427437447457467477487497507517527537547557567577587597607617627637647657667677687697707717727737747757767777787797807817827837847857867877887897907917927937947957967977987998008018028038048058068078088098108118128138148158168178188198208218228238248258268278288298308318328338348358368378388398408418428438448458468478488498508518528538548558568578588598608618628638648658668678688698708718728738748758768778788798808818828838848858868878888898908918928938948958968978988999009019029039049059069079089099109119129139149159169179189199209219229239249259269279289299309319329339349359369379389399409419429439449459469479489499509519529539549559569579589599609619629639649659669679689699709719729739749759769779789799809819829839849859869879889899909919929939949959969979989991000100110021003100410051006100710081009101010111012101310141015101610171018101910201021102210231024102510261027102810291030103110321033103410351036103710381039104010411042104310441045104610471048104910501051105210531054105510561057105810591060106110621063106410651066106710681069107010711072107310741075107610771078107910801081108210831084108510861087108810891090109110921093109410951096109710981099110011011102110311041105110611071108110911101111111211131114111511161117111811191120112111221123112411251126112711281129113011311132113311341135113611371138113911401141114211431144114511461147114811491150115111521153115411551156115711581159116011611162116311641165116611671168116911701171117211731174117511761177117811791180118111821183118411851186118711881189119011911192119311941195119611971198119912001201120212031204120512061207120812091210121112121213121412151216121712181219122012211222122312241225122612271228122912301231123212331234123512361237123812391240124112421243124412451246124712481249125012511252125312541255125612571258125912601261126212631264126512661267126812691270127112721273127412751276127712781279128012811282128312841285128612871288128912901291129212931294129512961297129812991300130113021303130413051306130713081309131013111312131313141315131613171318131913201321132213231324132513261327132813291330133113321333133413351336133713381339134013411342134313441345134613471348134913501351135213531354135513561357135813591360136113621363136413651366136713681369137013711372137313741375137613771378137913801381138213831384138513861387138813891390139113921393139413951396139713981399140014011402140314041405140614071408140914101411141214131414141514161417141814191420142114221423142414251426142714281429143014311432143314341435143614371438143914401441144214431444144514461447144814491450145114521453145414551456145714581459146014611462146314641465146614671468146914701471147214731474147514761477147814791480148114821483148414851486148714881489149014911492
  1. /** @file
  2. MMC/SD Card driver for OMAP 35xx (SDIO not supported)
  3. This driver always produces a BlockIo protocol but it starts off with no Media
  4. present. A TimerCallBack detects when media is inserted or removed and after
  5. a media change event a call to BlockIo ReadBlocks/WriteBlocks will cause the
  6. media to be detected (or removed) and the BlockIo Media structure will get
  7. updated. No MMC/SD Card harward registers are updated until the first BlockIo
  8. ReadBlocks/WriteBlocks after media has been insterted (booting with a card
  9. plugged in counts as an insertion event).
  10. Copyright (c) 2008 - 2009, Apple Inc. All rights reserved.<BR>
  11. SPDX-License-Identifier: BSD-2-Clause-Patent
  12. **/
  13. #include "MMCHS.h"
  14. EFI_BLOCK_IO_MEDIA gMMCHSMedia = {
  15. SIGNATURE_32('s','d','i','o'), // MediaId
  16. TRUE, // RemovableMedia
  17. FALSE, // MediaPresent
  18. FALSE, // LogicalPartition
  19. FALSE, // ReadOnly
  20. FALSE, // WriteCaching
  21. 512, // BlockSize
  22. 4, // IoAlign
  23. 0, // Pad
  24. 0 // LastBlock
  25. };
  26. typedef struct {
  27. VENDOR_DEVICE_PATH Mmc;
  28. EFI_DEVICE_PATH End;
  29. } MMCHS_DEVICE_PATH;
  30. MMCHS_DEVICE_PATH gMmcHsDevicePath = {
  31. {
  32. {
  33. HARDWARE_DEVICE_PATH,
  34. HW_VENDOR_DP,
  35. {
  36. (UINT8)(sizeof(VENDOR_DEVICE_PATH)),
  37. (UINT8)((sizeof(VENDOR_DEVICE_PATH)) >> 8),
  38. },
  39. },
  40. { 0xb615f1f5, 0x5088, 0x43cd, { 0x80, 0x9c, 0xa1, 0x6e, 0x52, 0x48, 0x7d, 0x00 } },
  41. },
  42. {
  43. END_DEVICE_PATH_TYPE,
  44. END_ENTIRE_DEVICE_PATH_SUBTYPE,
  45. { sizeof (EFI_DEVICE_PATH_PROTOCOL), 0 }
  46. }
  47. };
  48. CARD_INFO gCardInfo;
  49. EMBEDDED_EXTERNAL_DEVICE *gTPS65950;
  50. EFI_EVENT gTimerEvent;
  51. BOOLEAN gMediaChange = FALSE;
  52. //
  53. // Internal Functions
  54. //
  55. VOID
  56. ParseCardCIDData (
  57. UINT32 Response0,
  58. UINT32 Response1,
  59. UINT32 Response2,
  60. UINT32 Response3
  61. )
  62. {
  63. gCardInfo.CIDData.MDT = ((Response0 >> 8) & 0xFFF);
  64. gCardInfo.CIDData.PSN = (((Response0 >> 24) & 0xFF) | ((Response1 & 0xFFFFFF) << 8));
  65. gCardInfo.CIDData.PRV = ((Response1 >> 24) & 0xFF);
  66. gCardInfo.CIDData.PNM[4] = ((Response2) & 0xFF);
  67. gCardInfo.CIDData.PNM[3] = ((Response2 >> 8) & 0xFF);
  68. gCardInfo.CIDData.PNM[2] = ((Response2 >> 16) & 0xFF);
  69. gCardInfo.CIDData.PNM[1] = ((Response2 >> 24) & 0xFF);
  70. gCardInfo.CIDData.PNM[0] = ((Response3) & 0xFF);
  71. gCardInfo.CIDData.OID = ((Response3 >> 8) & 0xFFFF);
  72. gCardInfo.CIDData.MID = ((Response3 >> 24) & 0xFF);
  73. }
  74. VOID
  75. UpdateMMCHSClkFrequency (
  76. UINTN NewCLKD
  77. )
  78. {
  79. //Set Clock enable to 0x0 to not provide the clock to the card
  80. MmioAnd32 (MMCHS_SYSCTL, ~CEN);
  81. //Set new clock frequency.
  82. MmioAndThenOr32 (MMCHS_SYSCTL, ~CLKD_MASK, NewCLKD << 6);
  83. //Poll till Internal Clock Stable
  84. while ((MmioRead32 (MMCHS_SYSCTL) & ICS_MASK) != ICS);
  85. //Set Clock enable to 0x1 to provide the clock to the card
  86. MmioOr32 (MMCHS_SYSCTL, CEN);
  87. }
  88. EFI_STATUS
  89. SendCmd (
  90. UINTN Cmd,
  91. UINTN CmdInterruptEnableVal,
  92. UINTN CmdArgument
  93. )
  94. {
  95. UINTN MmcStatus;
  96. UINTN RetryCount = 0;
  97. //Check if command line is in use or not. Poll till command line is available.
  98. while ((MmioRead32 (MMCHS_PSTATE) & DATI_MASK) == DATI_NOT_ALLOWED);
  99. //Provide the block size.
  100. MmioWrite32 (MMCHS_BLK, BLEN_512BYTES);
  101. //Setting Data timeout counter value to max value.
  102. MmioAndThenOr32 (MMCHS_SYSCTL, ~DTO_MASK, DTO_VAL);
  103. //Clear Status register.
  104. MmioWrite32 (MMCHS_STAT, 0xFFFFFFFF);
  105. //Set command argument register
  106. MmioWrite32 (MMCHS_ARG, CmdArgument);
  107. //Enable interrupt enable events to occur
  108. MmioWrite32 (MMCHS_IE, CmdInterruptEnableVal);
  109. //Send a command
  110. MmioWrite32 (MMCHS_CMD, Cmd);
  111. //Check for the command status.
  112. while (RetryCount < MAX_RETRY_COUNT) {
  113. do {
  114. MmcStatus = MmioRead32 (MMCHS_STAT);
  115. } while (MmcStatus == 0);
  116. //Read status of command response
  117. if ((MmcStatus & ERRI) != 0) {
  118. //Perform soft-reset for mmci_cmd line.
  119. MmioOr32 (MMCHS_SYSCTL, SRC);
  120. while ((MmioRead32 (MMCHS_SYSCTL) & SRC));
  121. DEBUG ((EFI_D_INFO, "MmcStatus: %x\n", MmcStatus));
  122. return EFI_DEVICE_ERROR;
  123. }
  124. //Check if command is completed.
  125. if ((MmcStatus & CC) == CC) {
  126. MmioWrite32 (MMCHS_STAT, CC);
  127. break;
  128. }
  129. RetryCount++;
  130. }
  131. if (RetryCount == MAX_RETRY_COUNT) {
  132. return EFI_TIMEOUT;
  133. }
  134. return EFI_SUCCESS;
  135. }
  136. VOID
  137. GetBlockInformation (
  138. UINTN *BlockSize,
  139. UINTN *NumBlocks
  140. )
  141. {
  142. CSD_SDV2 *CsdSDV2Data;
  143. UINTN CardSize;
  144. if (gCardInfo.CardType == SD_CARD_2_HIGH) {
  145. CsdSDV2Data = (CSD_SDV2 *)&gCardInfo.CSDData;
  146. //Populate BlockSize.
  147. *BlockSize = (0x1UL << CsdSDV2Data->READ_BL_LEN);
  148. //Calculate Total number of blocks.
  149. CardSize = CsdSDV2Data->C_SIZELow16 | (CsdSDV2Data->C_SIZEHigh6 << 2);
  150. *NumBlocks = ((CardSize + 1) * 1024);
  151. } else {
  152. //Populate BlockSize.
  153. *BlockSize = (0x1UL << gCardInfo.CSDData.READ_BL_LEN);
  154. //Calculate Total number of blocks.
  155. CardSize = gCardInfo.CSDData.C_SIZELow2 | (gCardInfo.CSDData.C_SIZEHigh10 << 2);
  156. *NumBlocks = (CardSize + 1) * (1 << (gCardInfo.CSDData.C_SIZE_MULT + 2));
  157. }
  158. //For >=2G card, BlockSize may be 1K, but the transfer size is 512 bytes.
  159. if (*BlockSize > 512) {
  160. *NumBlocks = MultU64x32(*NumBlocks, *BlockSize/2);
  161. *BlockSize = 512;
  162. }
  163. DEBUG ((EFI_D_INFO, "Card type: %x, BlockSize: %x, NumBlocks: %x\n", gCardInfo.CardType, *BlockSize, *NumBlocks));
  164. }
  165. VOID
  166. CalculateCardCLKD (
  167. UINTN *ClockFrequencySelect
  168. )
  169. {
  170. UINT8 MaxDataTransferRate;
  171. UINTN TransferRateValue = 0;
  172. UINTN TimeValue = 0 ;
  173. UINTN Frequency = 0;
  174. MaxDataTransferRate = gCardInfo.CSDData.TRAN_SPEED;
  175. // For SD Cards we would need to send CMD6 to set
  176. // speeds abouve 25MHz. High Speed mode 50 MHz and up
  177. //Calculate Transfer rate unit (Bits 2:0 of TRAN_SPEED)
  178. switch (MaxDataTransferRate & 0x7) {
  179. case 0:
  180. TransferRateValue = 100 * 1000;
  181. break;
  182. case 1:
  183. TransferRateValue = 1 * 1000 * 1000;
  184. break;
  185. case 2:
  186. TransferRateValue = 10 * 1000 * 1000;
  187. break;
  188. case 3:
  189. TransferRateValue = 100 * 1000 * 1000;
  190. break;
  191. default:
  192. DEBUG((EFI_D_ERROR, "Invalid parameter.\n"));
  193. ASSERT(FALSE);
  194. }
  195. //Calculate Time value (Bits 6:3 of TRAN_SPEED)
  196. switch ((MaxDataTransferRate >> 3) & 0xF) {
  197. case 1:
  198. TimeValue = 10;
  199. break;
  200. case 2:
  201. TimeValue = 12;
  202. break;
  203. case 3:
  204. TimeValue = 13;
  205. break;
  206. case 4:
  207. TimeValue = 15;
  208. break;
  209. case 5:
  210. TimeValue = 20;
  211. break;
  212. case 6:
  213. TimeValue = 25;
  214. break;
  215. case 7:
  216. TimeValue = 30;
  217. break;
  218. case 8:
  219. TimeValue = 35;
  220. break;
  221. case 9:
  222. TimeValue = 40;
  223. break;
  224. case 10:
  225. TimeValue = 45;
  226. break;
  227. case 11:
  228. TimeValue = 50;
  229. break;
  230. case 12:
  231. TimeValue = 55;
  232. break;
  233. case 13:
  234. TimeValue = 60;
  235. break;
  236. case 14:
  237. TimeValue = 70;
  238. break;
  239. case 15:
  240. TimeValue = 80;
  241. break;
  242. default:
  243. DEBUG((EFI_D_ERROR, "Invalid parameter.\n"));
  244. ASSERT(FALSE);
  245. }
  246. Frequency = TransferRateValue * TimeValue/10;
  247. //Calculate Clock divider value to program in MMCHS_SYSCTL[CLKD] field.
  248. *ClockFrequencySelect = ((MMC_REFERENCE_CLK/Frequency) + 1);
  249. DEBUG ((EFI_D_INFO, "MaxDataTransferRate: 0x%x, Frequency: %d KHz, ClockFrequencySelect: %x\n", MaxDataTransferRate, Frequency/1000, *ClockFrequencySelect));
  250. }
  251. VOID
  252. GetCardConfigurationData (
  253. VOID
  254. )
  255. {
  256. UINTN BlockSize;
  257. UINTN NumBlocks;
  258. UINTN ClockFrequencySelect;
  259. //Calculate BlockSize and Total number of blocks in the detected card.
  260. GetBlockInformation(&BlockSize, &NumBlocks);
  261. gCardInfo.BlockSize = BlockSize;
  262. gCardInfo.NumBlocks = NumBlocks;
  263. //Calculate Card clock divider value.
  264. CalculateCardCLKD(&ClockFrequencySelect);
  265. gCardInfo.ClockFrequencySelect = ClockFrequencySelect;
  266. }
  267. EFI_STATUS
  268. InitializeMMCHS (
  269. VOID
  270. )
  271. {
  272. UINT8 Data = 0;
  273. EFI_STATUS Status;
  274. //Select Device group to belong to P1 device group in Power IC.
  275. Data = DEV_GRP_P1;
  276. Status = gTPS65950->Write (gTPS65950, EXTERNAL_DEVICE_REGISTER(I2C_ADDR_GRP_ID4, VMMC1_DEV_GRP), 1, &Data);
  277. ASSERT_EFI_ERROR(Status);
  278. //Configure voltage regulator for MMC1 in Power IC to output 3.0 voltage.
  279. Data = VSEL_3_00V;
  280. Status = gTPS65950->Write (gTPS65950, EXTERNAL_DEVICE_REGISTER(I2C_ADDR_GRP_ID4, VMMC1_DEDICATED_REG), 1, &Data);
  281. ASSERT_EFI_ERROR(Status);
  282. //After ramping up voltage, set VDDS stable bit to indicate that voltage level is stable.
  283. MmioOr32 (CONTROL_PBIAS_LITE, (PBIASLITEVMODE0 | PBIASLITEPWRDNZ0 | PBIASSPEEDCTRL0 | PBIASLITEVMODE1 | PBIASLITEWRDNZ1));
  284. // Enable WP GPIO
  285. MmioAndThenOr32 (GPIO1_BASE + GPIO_OE, ~BIT23, BIT23);
  286. // Enable Card Detect
  287. Data = CARD_DETECT_ENABLE;
  288. gTPS65950->Write (gTPS65950, EXTERNAL_DEVICE_REGISTER(I2C_ADDR_GRP_ID2, TPS65950_GPIO_CTRL), 1, &Data);
  289. return Status;
  290. }
  291. EFI_STATUS
  292. PerformCardIdenfication (
  293. VOID
  294. )
  295. {
  296. EFI_STATUS Status;
  297. UINTN CmdArgument = 0;
  298. UINTN Response = 0;
  299. UINTN RetryCount = 0;
  300. BOOLEAN SDCmd8Supported = FALSE;
  301. //Enable interrupts.
  302. MmioWrite32 (MMCHS_IE, (BADA_EN | CERR_EN | DEB_EN | DCRC_EN | DTO_EN | CIE_EN |
  303. CEB_EN | CCRC_EN | CTO_EN | BRR_EN | BWR_EN | TC_EN | CC_EN));
  304. //Controller INIT procedure start.
  305. MmioOr32 (MMCHS_CON, INIT);
  306. MmioWrite32 (MMCHS_CMD, 0x00000000);
  307. while (!(MmioRead32 (MMCHS_STAT) & CC));
  308. //Wait for 1 ms
  309. gBS->Stall(1000);
  310. //Set CC bit to 0x1 to clear the flag
  311. MmioOr32 (MMCHS_STAT, CC);
  312. //Retry INIT procedure.
  313. MmioWrite32 (MMCHS_CMD, 0x00000000);
  314. while (!(MmioRead32 (MMCHS_STAT) & CC));
  315. //End initialization sequence
  316. MmioAnd32 (MMCHS_CON, ~INIT);
  317. MmioOr32 (MMCHS_HCTL, (SDVS_3_0_V | DTW_1_BIT | SDBP_ON));
  318. //Change clock frequency to 400KHz to fit protocol
  319. UpdateMMCHSClkFrequency(CLKD_400KHZ);
  320. MmioOr32 (MMCHS_CON, OD);
  321. //Send CMD0 command.
  322. Status = SendCmd (CMD0, CMD0_INT_EN, CmdArgument);
  323. if (EFI_ERROR(Status)) {
  324. DEBUG ((EFI_D_ERROR, "Cmd0 fails.\n"));
  325. return Status;
  326. }
  327. DEBUG ((EFI_D_INFO, "CMD0 response: %x\n", MmioRead32 (MMCHS_RSP10)));
  328. //Send CMD5 command.
  329. Status = SendCmd (CMD5, CMD5_INT_EN, CmdArgument);
  330. if (Status == EFI_SUCCESS) {
  331. DEBUG ((EFI_D_ERROR, "CMD5 Success. SDIO card. Follow SDIO card specification.\n"));
  332. DEBUG ((EFI_D_INFO, "CMD5 response: %x\n", MmioRead32 (MMCHS_RSP10)));
  333. //NOTE: Returning unsupported error for now. Need to implement SDIO specification.
  334. return EFI_UNSUPPORTED;
  335. } else {
  336. DEBUG ((EFI_D_INFO, "CMD5 fails. Not an SDIO card.\n"));
  337. }
  338. MmioOr32 (MMCHS_SYSCTL, SRC);
  339. gBS->Stall(1000);
  340. while ((MmioRead32 (MMCHS_SYSCTL) & SRC));
  341. //Send CMD8 command. (New v2.00 command for Voltage check)
  342. //Only 2.7V - 3.6V is supported for SD2.0, only SD 2.0 card can pass.
  343. //MMC & SD1.1 card will fail this command.
  344. CmdArgument = CMD8_ARG;
  345. Status = SendCmd (CMD8, CMD8_INT_EN, CmdArgument);
  346. if (Status == EFI_SUCCESS) {
  347. Response = MmioRead32 (MMCHS_RSP10);
  348. DEBUG ((EFI_D_INFO, "CMD8 success. CMD8 response: %x\n", Response));
  349. if (Response != CmdArgument) {
  350. return EFI_DEVICE_ERROR;
  351. }
  352. DEBUG ((EFI_D_INFO, "Card is SD2.0\n"));
  353. SDCmd8Supported = TRUE; //Supports high capacity.
  354. } else {
  355. DEBUG ((EFI_D_INFO, "CMD8 fails. Not an SD2.0 card.\n"));
  356. }
  357. MmioOr32 (MMCHS_SYSCTL, SRC);
  358. gBS->Stall(1000);
  359. while ((MmioRead32 (MMCHS_SYSCTL) & SRC));
  360. //Poll till card is busy
  361. while (RetryCount < MAX_RETRY_COUNT) {
  362. //Send CMD55 command.
  363. CmdArgument = 0;
  364. Status = SendCmd (CMD55, CMD55_INT_EN, CmdArgument);
  365. if (Status == EFI_SUCCESS) {
  366. DEBUG ((EFI_D_INFO, "CMD55 success. CMD55 response: %x\n", MmioRead32 (MMCHS_RSP10)));
  367. gCardInfo.CardType = SD_CARD;
  368. } else {
  369. DEBUG ((EFI_D_INFO, "CMD55 fails.\n"));
  370. gCardInfo.CardType = MMC_CARD;
  371. }
  372. //Send appropriate command for the card type which got detected.
  373. if (gCardInfo.CardType == SD_CARD) {
  374. CmdArgument = ((UINTN *) &(gCardInfo.OCRData))[0];
  375. //Set HCS bit.
  376. if (SDCmd8Supported) {
  377. CmdArgument |= HCS;
  378. }
  379. Status = SendCmd (ACMD41, ACMD41_INT_EN, CmdArgument);
  380. if (EFI_ERROR(Status)) {
  381. DEBUG ((EFI_D_INFO, "ACMD41 fails.\n"));
  382. return Status;
  383. }
  384. ((UINT32 *) &(gCardInfo.OCRData))[0] = MmioRead32 (MMCHS_RSP10);
  385. DEBUG ((EFI_D_INFO, "SD card detected. ACMD41 OCR: %x\n", ((UINT32 *) &(gCardInfo.OCRData))[0]));
  386. } else if (gCardInfo.CardType == MMC_CARD) {
  387. CmdArgument = 0;
  388. Status = SendCmd (CMD1, CMD1_INT_EN, CmdArgument);
  389. if (EFI_ERROR(Status)) {
  390. DEBUG ((EFI_D_INFO, "CMD1 fails.\n"));
  391. return Status;
  392. }
  393. Response = MmioRead32 (MMCHS_RSP10);
  394. DEBUG ((EFI_D_INFO, "MMC card detected.. CMD1 response: %x\n", Response));
  395. //NOTE: For now, I am skipping this since I only have an SD card.
  396. //Compare card OCR and host OCR (Section 22.6.1.3.2.4)
  397. return EFI_UNSUPPORTED; //For now, MMC is not supported.
  398. }
  399. //Poll the card until it is out of its power-up sequence.
  400. if (gCardInfo.OCRData.Busy == 1) {
  401. if (SDCmd8Supported) {
  402. gCardInfo.CardType = SD_CARD_2;
  403. }
  404. //Card is ready. Check CCS (Card capacity status) bit (bit#30).
  405. //SD 2.0 standard card will response with CCS 0, SD high capacity card will respond with CCS 1.
  406. if (gCardInfo.OCRData.AccessMode & BIT1) {
  407. gCardInfo.CardType = SD_CARD_2_HIGH;
  408. DEBUG ((EFI_D_INFO, "High capacity card.\n"));
  409. } else {
  410. DEBUG ((EFI_D_INFO, "Standard capacity card.\n"));
  411. }
  412. break;
  413. }
  414. gBS->Stall(1000);
  415. RetryCount++;
  416. }
  417. if (RetryCount == MAX_RETRY_COUNT) {
  418. DEBUG ((EFI_D_ERROR, "Timeout error. RetryCount: %d\n", RetryCount));
  419. return EFI_TIMEOUT;
  420. }
  421. //Read CID data.
  422. CmdArgument = 0;
  423. Status = SendCmd (CMD2, CMD2_INT_EN, CmdArgument);
  424. if (EFI_ERROR(Status)) {
  425. DEBUG ((EFI_D_ERROR, "CMD2 fails. Status: %x\n", Status));
  426. return Status;
  427. }
  428. DEBUG ((EFI_D_INFO, "CMD2 response: %x %x %x %x\n", MmioRead32 (MMCHS_RSP10), MmioRead32 (MMCHS_RSP32), MmioRead32 (MMCHS_RSP54), MmioRead32 (MMCHS_RSP76)));
  429. //Parse CID register data.
  430. ParseCardCIDData(MmioRead32 (MMCHS_RSP10), MmioRead32 (MMCHS_RSP32), MmioRead32 (MMCHS_RSP54), MmioRead32 (MMCHS_RSP76));
  431. //Read RCA
  432. CmdArgument = 0;
  433. Status = SendCmd (CMD3, CMD3_INT_EN, CmdArgument);
  434. if (EFI_ERROR(Status)) {
  435. DEBUG ((EFI_D_ERROR, "CMD3 fails. Status: %x\n", Status));
  436. return Status;
  437. }
  438. //Set RCA for the detected card. RCA is CMD3 response.
  439. gCardInfo.RCA = (MmioRead32 (MMCHS_RSP10) >> 16);
  440. DEBUG ((EFI_D_INFO, "CMD3 response: RCA %x\n", gCardInfo.RCA));
  441. //MMC Bus setting change after card identification.
  442. MmioAnd32 (MMCHS_CON, ~OD);
  443. MmioOr32 (MMCHS_HCTL, SDVS_3_0_V);
  444. UpdateMMCHSClkFrequency(CLKD_400KHZ); //Set the clock frequency to 400KHz.
  445. return EFI_SUCCESS;
  446. }
  447. EFI_STATUS
  448. GetCardSpecificData (
  449. VOID
  450. )
  451. {
  452. EFI_STATUS Status;
  453. UINTN CmdArgument;
  454. //Send CMD9 to retrieve CSD.
  455. CmdArgument = gCardInfo.RCA << 16;
  456. Status = SendCmd (CMD9, CMD9_INT_EN, CmdArgument);
  457. if (EFI_ERROR(Status)) {
  458. DEBUG ((EFI_D_ERROR, "CMD9 fails. Status: %x\n", Status));
  459. return Status;
  460. }
  461. //Populate 128-bit CSD register data.
  462. ((UINT32 *)&(gCardInfo.CSDData))[0] = MmioRead32 (MMCHS_RSP10);
  463. ((UINT32 *)&(gCardInfo.CSDData))[1] = MmioRead32 (MMCHS_RSP32);
  464. ((UINT32 *)&(gCardInfo.CSDData))[2] = MmioRead32 (MMCHS_RSP54);
  465. ((UINT32 *)&(gCardInfo.CSDData))[3] = MmioRead32 (MMCHS_RSP76);
  466. DEBUG ((EFI_D_INFO, "CMD9 response: %x %x %x %x\n", MmioRead32 (MMCHS_RSP10), MmioRead32 (MMCHS_RSP32), MmioRead32 (MMCHS_RSP54), MmioRead32 (MMCHS_RSP76)));
  467. //Calculate total number of blocks and max. data transfer rate supported by the detected card.
  468. GetCardConfigurationData();
  469. return Status;
  470. }
  471. EFI_STATUS
  472. PerformCardConfiguration (
  473. VOID
  474. )
  475. {
  476. UINTN CmdArgument = 0;
  477. EFI_STATUS Status;
  478. //Send CMD7
  479. CmdArgument = gCardInfo.RCA << 16;
  480. Status = SendCmd (CMD7, CMD7_INT_EN, CmdArgument);
  481. if (EFI_ERROR(Status)) {
  482. DEBUG ((EFI_D_ERROR, "CMD7 fails. Status: %x\n", Status));
  483. return Status;
  484. }
  485. if ((gCardInfo.CardType != UNKNOWN_CARD) && (gCardInfo.CardType != MMC_CARD)) {
  486. // We could read SCR register, but SD Card Phys spec stats any SD Card shall
  487. // set SCR.SD_BUS_WIDTHS to support 4-bit mode, so why bother?
  488. // Send ACMD6 (application specific commands must be prefixed with CMD55)
  489. Status = SendCmd (CMD55, CMD55_INT_EN, CmdArgument);
  490. if (!EFI_ERROR (Status)) {
  491. // set device into 4-bit data bus mode
  492. Status = SendCmd (ACMD6, ACMD6_INT_EN, 0x2);
  493. if (!EFI_ERROR (Status)) {
  494. // Set host controler into 4-bit mode
  495. MmioOr32 (MMCHS_HCTL, DTW_4_BIT);
  496. DEBUG ((EFI_D_INFO, "SD Memory Card set to 4-bit mode\n"));
  497. }
  498. }
  499. }
  500. //Send CMD16 to set the block length
  501. CmdArgument = gCardInfo.BlockSize;
  502. Status = SendCmd (CMD16, CMD16_INT_EN, CmdArgument);
  503. if (EFI_ERROR(Status)) {
  504. DEBUG ((EFI_D_ERROR, "CMD16 fails. Status: %x\n", Status));
  505. return Status;
  506. }
  507. //Change MMCHS clock frequency to what detected card can support.
  508. UpdateMMCHSClkFrequency(gCardInfo.ClockFrequencySelect);
  509. return EFI_SUCCESS;
  510. }
  511. EFI_STATUS
  512. ReadBlockData (
  513. IN EFI_BLOCK_IO_PROTOCOL *This,
  514. OUT VOID *Buffer
  515. )
  516. {
  517. UINTN MmcStatus;
  518. UINTN *DataBuffer = Buffer;
  519. UINTN DataSize = This->Media->BlockSize/4;
  520. UINTN Count;
  521. UINTN RetryCount = 0;
  522. //Check controller status to make sure there is no error.
  523. while (RetryCount < MAX_RETRY_COUNT) {
  524. do {
  525. //Read Status.
  526. MmcStatus = MmioRead32 (MMCHS_STAT);
  527. } while(MmcStatus == 0);
  528. //Check if Buffer read ready (BRR) bit is set?
  529. if (MmcStatus & BRR) {
  530. //Clear BRR bit
  531. MmioOr32 (MMCHS_STAT, BRR);
  532. //Read block worth of data.
  533. for (Count = 0; Count < DataSize; Count++) {
  534. *DataBuffer++ = MmioRead32 (MMCHS_DATA);
  535. }
  536. break;
  537. }
  538. RetryCount++;
  539. }
  540. if (RetryCount == MAX_RETRY_COUNT) {
  541. return EFI_TIMEOUT;
  542. }
  543. return EFI_SUCCESS;
  544. }
  545. EFI_STATUS
  546. WriteBlockData (
  547. IN EFI_BLOCK_IO_PROTOCOL *This,
  548. OUT VOID *Buffer
  549. )
  550. {
  551. UINTN MmcStatus;
  552. UINTN *DataBuffer = Buffer;
  553. UINTN DataSize = This->Media->BlockSize/4;
  554. UINTN Count;
  555. UINTN RetryCount = 0;
  556. //Check controller status to make sure there is no error.
  557. while (RetryCount < MAX_RETRY_COUNT) {
  558. do {
  559. //Read Status.
  560. MmcStatus = MmioRead32 (MMCHS_STAT);
  561. } while(MmcStatus == 0);
  562. //Check if Buffer write ready (BWR) bit is set?
  563. if (MmcStatus & BWR) {
  564. //Clear BWR bit
  565. MmioOr32 (MMCHS_STAT, BWR);
  566. //Write block worth of data.
  567. for (Count = 0; Count < DataSize; Count++) {
  568. MmioWrite32 (MMCHS_DATA, *DataBuffer++);
  569. }
  570. break;
  571. }
  572. RetryCount++;
  573. }
  574. if (RetryCount == MAX_RETRY_COUNT) {
  575. return EFI_TIMEOUT;
  576. }
  577. return EFI_SUCCESS;
  578. }
  579. EFI_STATUS
  580. DmaBlocks (
  581. IN EFI_BLOCK_IO_PROTOCOL *This,
  582. IN UINTN Lba,
  583. IN OUT VOID *Buffer,
  584. IN UINTN BlockCount,
  585. IN OPERATION_TYPE OperationType
  586. )
  587. {
  588. EFI_STATUS Status;
  589. UINTN DmaSize = 0;
  590. UINTN Cmd = 0;
  591. UINTN CmdInterruptEnable;
  592. UINTN CmdArgument;
  593. VOID *BufferMap;
  594. EFI_PHYSICAL_ADDRESS BufferAddress;
  595. OMAP_DMA4 Dma4;
  596. DMA_MAP_OPERATION DmaOperation;
  597. EFI_STATUS MmcStatus;
  598. UINTN RetryCount = 0;
  599. CpuDeadLoop ();
  600. // Map passed in buffer for DMA xfer
  601. DmaSize = BlockCount * This->Media->BlockSize;
  602. Status = DmaMap (DmaOperation, Buffer, &DmaSize, &BufferAddress, &BufferMap);
  603. if (EFI_ERROR (Status)) {
  604. return Status;
  605. }
  606. ZeroMem (&DmaOperation, sizeof (DMA_MAP_OPERATION));
  607. Dma4.DataType = 2; // DMA4_CSDPi[1:0] 32-bit elements from MMCHS_DATA
  608. Dma4.SourceEndiansim = 0; // DMA4_CSDPi[21]
  609. Dma4.DestinationEndianism = 0; // DMA4_CSDPi[19]
  610. Dma4.SourcePacked = 0; // DMA4_CSDPi[6]
  611. Dma4.DestinationPacked = 0; // DMA4_CSDPi[13]
  612. Dma4.NumberOfElementPerFrame = This->Media->BlockSize/4; // DMA4_CENi (TRM 4K is optimum value)
  613. Dma4.NumberOfFramePerTransferBlock = BlockCount; // DMA4_CFNi
  614. Dma4.ReadPriority = 0; // DMA4_CCRi[6] Low priority read
  615. Dma4.WritePriority = 0; // DMA4_CCRi[23] Prefetech disabled
  616. //Populate the command information based on the operation type.
  617. if (OperationType == READ) {
  618. Cmd = CMD18; //Multiple block read
  619. CmdInterruptEnable = CMD18_INT_EN;
  620. DmaOperation = MapOperationBusMasterCommonBuffer;
  621. Dma4.ReadPortAccessType =0 ; // DMA4_CSDPi[8:7] Can not burst MMCHS_DATA reg
  622. Dma4.WritePortAccessType = 3; // DMA4_CSDPi[15:14] Memory burst 16x32
  623. Dma4.WriteMode = 1; // DMA4_CSDPi[17:16] Write posted
  624. Dma4.SourceStartAddress = MMCHS_DATA; // DMA4_CSSAi
  625. Dma4.DestinationStartAddress = (UINT32)BufferAddress; // DMA4_CDSAi
  626. Dma4.SourceElementIndex = 1; // DMA4_CSEi
  627. Dma4.SourceFrameIndex = 0x200; // DMA4_CSFi
  628. Dma4.DestinationElementIndex = 1; // DMA4_CDEi
  629. Dma4.DestinationFrameIndex = 0; // DMA4_CDFi
  630. Dma4.ReadPortAccessMode = 0; // DMA4_CCRi[13:12] Always read MMCHS_DATA
  631. Dma4.WritePortAccessMode = 1; // DMA4_CCRi[15:14] Post increment memory address
  632. Dma4.ReadRequestNumber = 0x1e; // DMA4_CCRi[4:0] Syncro with MMCA_DMA_RX (61)
  633. Dma4.WriteRequestNumber = 1; // DMA4_CCRi[20:19] Syncro upper 0x3e == 62 (one based)
  634. } else if (OperationType == WRITE) {
  635. Cmd = CMD25; //Multiple block write
  636. CmdInterruptEnable = CMD25_INT_EN;
  637. DmaOperation = MapOperationBusMasterRead;
  638. Dma4.ReadPortAccessType = 3; // DMA4_CSDPi[8:7] Memory burst 16x32
  639. Dma4.WritePortAccessType = 0; // DMA4_CSDPi[15:14] Can not burst MMCHS_DATA reg
  640. Dma4.WriteMode = 1; // DMA4_CSDPi[17:16] Write posted ???
  641. Dma4.SourceStartAddress = (UINT32)BufferAddress; // DMA4_CSSAi
  642. Dma4.DestinationStartAddress = MMCHS_DATA; // DMA4_CDSAi
  643. Dma4.SourceElementIndex = 1; // DMA4_CSEi
  644. Dma4.SourceFrameIndex = 0x200; // DMA4_CSFi
  645. Dma4.DestinationElementIndex = 1; // DMA4_CDEi
  646. Dma4.DestinationFrameIndex = 0; // DMA4_CDFi
  647. Dma4.ReadPortAccessMode = 1; // DMA4_CCRi[13:12] Post increment memory address
  648. Dma4.WritePortAccessMode = 0; // DMA4_CCRi[15:14] Always write MMCHS_DATA
  649. Dma4.ReadRequestNumber = 0x1d; // DMA4_CCRi[4:0] Syncro with MMCA_DMA_TX (60)
  650. Dma4.WriteRequestNumber = 1; // DMA4_CCRi[20:19] Syncro upper 0x3d == 61 (one based)
  651. } else {
  652. return EFI_INVALID_PARAMETER;
  653. }
  654. EnableDmaChannel (2, &Dma4);
  655. //Set command argument based on the card access mode (Byte mode or Block mode)
  656. if (gCardInfo.OCRData.AccessMode & BIT1) {
  657. CmdArgument = Lba;
  658. } else {
  659. CmdArgument = Lba * This->Media->BlockSize;
  660. }
  661. //Send Command.
  662. Status = SendCmd (Cmd, CmdInterruptEnable, CmdArgument);
  663. if (EFI_ERROR (Status)) {
  664. DEBUG ((EFI_D_ERROR, "CMD fails. Status: %x\n", Status));
  665. return Status;
  666. }
  667. //Check for the Transfer completion.
  668. while (RetryCount < MAX_RETRY_COUNT) {
  669. //Read Status
  670. do {
  671. MmcStatus = MmioRead32 (MMCHS_STAT);
  672. } while (MmcStatus == 0);
  673. //Check if Transfer complete (TC) bit is set?
  674. if (MmcStatus & TC) {
  675. break;
  676. } else {
  677. DEBUG ((EFI_D_ERROR, "MmcStatus for TC: %x\n", MmcStatus));
  678. //Check if DEB, DCRC or DTO interrupt occured.
  679. if ((MmcStatus & DEB) | (MmcStatus & DCRC) | (MmcStatus & DTO)) {
  680. //There was an error during the data transfer.
  681. //Set SRD bit to 1 and wait until it return to 0x0.
  682. MmioOr32 (MMCHS_SYSCTL, SRD);
  683. while((MmioRead32 (MMCHS_SYSCTL) & SRD) != 0x0);
  684. DisableDmaChannel (2, DMA4_CSR_BLOCK, DMA4_CSR_ERR);
  685. DmaUnmap (BufferMap);
  686. return EFI_DEVICE_ERROR;
  687. }
  688. }
  689. RetryCount++;
  690. }
  691. DisableDmaChannel (2, DMA4_CSR_BLOCK, DMA4_CSR_ERR);
  692. Status = DmaUnmap (BufferMap);
  693. if (RetryCount == MAX_RETRY_COUNT) {
  694. DEBUG ((EFI_D_ERROR, "TransferBlockData timed out.\n"));
  695. return EFI_TIMEOUT;
  696. }
  697. return Status;
  698. }
  699. EFI_STATUS
  700. TransferBlock (
  701. IN EFI_BLOCK_IO_PROTOCOL *This,
  702. IN UINTN Lba,
  703. IN OUT VOID *Buffer,
  704. IN OPERATION_TYPE OperationType
  705. )
  706. {
  707. EFI_STATUS Status;
  708. UINTN MmcStatus;
  709. UINTN RetryCount = 0;
  710. UINTN Cmd = 0;
  711. UINTN CmdInterruptEnable = 0;
  712. UINTN CmdArgument = 0;
  713. //Populate the command information based on the operation type.
  714. if (OperationType == READ) {
  715. Cmd = CMD17; //Single block read
  716. CmdInterruptEnable = CMD18_INT_EN;
  717. } else if (OperationType == WRITE) {
  718. Cmd = CMD24; //Single block write
  719. CmdInterruptEnable = CMD24_INT_EN;
  720. }
  721. //Set command argument based on the card access mode (Byte mode or Block mode)
  722. if (gCardInfo.OCRData.AccessMode & BIT1) {
  723. CmdArgument = Lba;
  724. } else {
  725. CmdArgument = Lba * This->Media->BlockSize;
  726. }
  727. //Send Command.
  728. Status = SendCmd (Cmd, CmdInterruptEnable, CmdArgument);
  729. if (EFI_ERROR(Status)) {
  730. DEBUG ((EFI_D_ERROR, "CMD fails. Status: %x\n", Status));
  731. return Status;
  732. }
  733. //Read or Write data.
  734. if (OperationType == READ) {
  735. Status = ReadBlockData (This, Buffer);
  736. if (EFI_ERROR(Status)) {
  737. DEBUG((EFI_D_ERROR, "ReadBlockData fails.\n"));
  738. return Status;
  739. }
  740. } else if (OperationType == WRITE) {
  741. Status = WriteBlockData (This, Buffer);
  742. if (EFI_ERROR(Status)) {
  743. DEBUG((EFI_D_ERROR, "WriteBlockData fails.\n"));
  744. return Status;
  745. }
  746. }
  747. //Check for the Transfer completion.
  748. while (RetryCount < MAX_RETRY_COUNT) {
  749. //Read Status
  750. do {
  751. MmcStatus = MmioRead32 (MMCHS_STAT);
  752. } while (MmcStatus == 0);
  753. //Check if Transfer complete (TC) bit is set?
  754. if (MmcStatus & TC) {
  755. break;
  756. } else {
  757. DEBUG ((EFI_D_ERROR, "MmcStatus for TC: %x\n", MmcStatus));
  758. //Check if DEB, DCRC or DTO interrupt occured.
  759. if ((MmcStatus & DEB) | (MmcStatus & DCRC) | (MmcStatus & DTO)) {
  760. //There was an error during the data transfer.
  761. //Set SRD bit to 1 and wait until it return to 0x0.
  762. MmioOr32 (MMCHS_SYSCTL, SRD);
  763. while((MmioRead32 (MMCHS_SYSCTL) & SRD) != 0x0);
  764. return EFI_DEVICE_ERROR;
  765. }
  766. }
  767. RetryCount++;
  768. }
  769. if (RetryCount == MAX_RETRY_COUNT) {
  770. DEBUG ((EFI_D_ERROR, "TransferBlockData timed out.\n"));
  771. return EFI_TIMEOUT;
  772. }
  773. return EFI_SUCCESS;
  774. }
  775. BOOLEAN
  776. CardPresent (
  777. VOID
  778. )
  779. {
  780. EFI_STATUS Status;
  781. UINT8 Data;
  782. //
  783. // Card detect is a GPIO0 on the TPS65950
  784. //
  785. Status = gTPS65950->Read (gTPS65950, EXTERNAL_DEVICE_REGISTER(I2C_ADDR_GRP_ID2, GPIODATAIN1), 1, &Data);
  786. if (EFI_ERROR (Status)) {
  787. return FALSE;
  788. }
  789. if ((Data & CARD_DETECT_BIT) == CARD_DETECT_BIT) {
  790. // No Card present
  791. return FALSE;
  792. } else {
  793. return TRUE;
  794. }
  795. }
  796. EFI_STATUS
  797. DetectCard (
  798. VOID
  799. )
  800. {
  801. EFI_STATUS Status;
  802. if (!CardPresent ()) {
  803. return EFI_NO_MEDIA;
  804. }
  805. //Initialize MMC host controller clocks.
  806. Status = InitializeMMCHS ();
  807. if (EFI_ERROR(Status)) {
  808. DEBUG ((EFI_D_ERROR, "Initialize MMC host controller fails. Status: %x\n", Status));
  809. return Status;
  810. }
  811. //Software reset of the MMCHS host controller.
  812. MmioWrite32 (MMCHS_SYSCONFIG, SOFTRESET);
  813. gBS->Stall(1000);
  814. while ((MmioRead32 (MMCHS_SYSSTATUS) & RESETDONE_MASK) != RESETDONE);
  815. //Soft reset for all.
  816. MmioWrite32 (MMCHS_SYSCTL, SRA);
  817. gBS->Stall(1000);
  818. while ((MmioRead32 (MMCHS_SYSCTL) & SRA) != 0x0);
  819. //Voltage capabilities initialization. Activate VS18 and VS30.
  820. MmioOr32 (MMCHS_CAPA, (VS30 | VS18));
  821. //Wakeup configuration
  822. MmioOr32 (MMCHS_SYSCONFIG, ENAWAKEUP);
  823. MmioOr32 (MMCHS_HCTL, IWE);
  824. //MMCHS Controller default initialization
  825. MmioOr32 (MMCHS_CON, (OD | DW8_1_4_BIT | CEATA_OFF));
  826. MmioWrite32 (MMCHS_HCTL, (SDVS_3_0_V | DTW_1_BIT | SDBP_OFF));
  827. //Enable internal clock
  828. MmioOr32 (MMCHS_SYSCTL, ICE);
  829. //Set the clock frequency to 80KHz.
  830. UpdateMMCHSClkFrequency (CLKD_80KHZ);
  831. //Enable SD bus power.
  832. MmioOr32 (MMCHS_HCTL, (SDBP_ON));
  833. //Poll till SD bus power bit is set.
  834. while ((MmioRead32 (MMCHS_HCTL) & SDBP_MASK) != SDBP_ON);
  835. //Card idenfication
  836. Status = PerformCardIdenfication ();
  837. if (EFI_ERROR(Status)) {
  838. DEBUG ((EFI_D_ERROR, "No MMC/SD card detected.\n"));
  839. return Status;
  840. }
  841. //Get CSD (Card specific data) for the detected card.
  842. Status = GetCardSpecificData();
  843. if (EFI_ERROR(Status)) {
  844. return Status;
  845. }
  846. //Configure the card in data transfer mode.
  847. Status = PerformCardConfiguration();
  848. if (EFI_ERROR(Status)) {
  849. return Status;
  850. }
  851. //Patch the Media structure.
  852. gMMCHSMedia.LastBlock = (gCardInfo.NumBlocks - 1);
  853. gMMCHSMedia.BlockSize = gCardInfo.BlockSize;
  854. gMMCHSMedia.ReadOnly = (MmioRead32 (GPIO1_BASE + GPIO_DATAIN) & BIT23) == BIT23;
  855. gMMCHSMedia.MediaPresent = TRUE;
  856. gMMCHSMedia.MediaId++;
  857. DEBUG ((EFI_D_INFO, "SD Card Media Change on Handle 0x%08x\n", gImageHandle));
  858. return Status;
  859. }
  860. #define MAX_MMCHS_TRANSFER_SIZE 0x4000
  861. EFI_STATUS
  862. SdReadWrite (
  863. IN EFI_BLOCK_IO_PROTOCOL *This,
  864. IN UINTN Lba,
  865. OUT VOID *Buffer,
  866. IN UINTN BufferSize,
  867. IN OPERATION_TYPE OperationType
  868. )
  869. {
  870. EFI_STATUS Status = EFI_SUCCESS;
  871. UINTN RetryCount = 0;
  872. UINTN BlockCount;
  873. UINTN BytesToBeTranferedThisPass = 0;
  874. UINTN BytesRemainingToBeTransfered;
  875. EFI_TPL OldTpl;
  876. BOOLEAN Update;
  877. Update = FALSE;
  878. if (gMediaChange) {
  879. Update = TRUE;
  880. Status = DetectCard ();
  881. if (EFI_ERROR (Status)) {
  882. // We detected a removal
  883. gMMCHSMedia.MediaPresent = FALSE;
  884. gMMCHSMedia.LastBlock = 0;
  885. gMMCHSMedia.BlockSize = 512; // Should be zero but there is a bug in DiskIo
  886. gMMCHSMedia.ReadOnly = FALSE;
  887. }
  888. gMediaChange = FALSE;
  889. } else if (!gMMCHSMedia.MediaPresent) {
  890. Status = EFI_NO_MEDIA;
  891. goto Done;
  892. }
  893. if (Update) {
  894. DEBUG ((EFI_D_INFO, "SD Card ReinstallProtocolInterface ()\n"));
  895. gBS->ReinstallProtocolInterface (
  896. gImageHandle,
  897. &gEfiBlockIoProtocolGuid,
  898. &gBlockIo,
  899. &gBlockIo
  900. );
  901. return EFI_MEDIA_CHANGED;
  902. }
  903. if (EFI_ERROR (Status)) {
  904. goto Done;
  905. }
  906. if (Buffer == NULL) {
  907. Status = EFI_INVALID_PARAMETER;
  908. goto Done;
  909. }
  910. if (Lba > This->Media->LastBlock) {
  911. Status = EFI_INVALID_PARAMETER;
  912. goto Done;
  913. }
  914. if ((BufferSize % This->Media->BlockSize) != 0) {
  915. Status = EFI_BAD_BUFFER_SIZE;
  916. goto Done;
  917. }
  918. //Check if the data lines are not in use.
  919. while ((RetryCount++ < MAX_RETRY_COUNT) && ((MmioRead32 (MMCHS_PSTATE) & DATI_MASK) != DATI_ALLOWED));
  920. if (RetryCount == MAX_RETRY_COUNT) {
  921. Status = EFI_TIMEOUT;
  922. goto Done;
  923. }
  924. OldTpl = gBS->RaiseTPL (TPL_NOTIFY);
  925. BytesRemainingToBeTransfered = BufferSize;
  926. while (BytesRemainingToBeTransfered > 0) {
  927. if (gMediaChange) {
  928. Status = EFI_NO_MEDIA;
  929. DEBUG ((EFI_D_INFO, "SdReadWrite() EFI_NO_MEDIA due to gMediaChange\n"));
  930. goto DoneRestoreTPL;
  931. }
  932. // Turn OFF DMA path until it is debugged
  933. // BytesToBeTranferedThisPass = (BytesToBeTranferedThisPass >= MAX_MMCHS_TRANSFER_SIZE) ? MAX_MMCHS_TRANSFER_SIZE : BytesRemainingToBeTransfered;
  934. BytesToBeTranferedThisPass = This->Media->BlockSize;
  935. BlockCount = BytesToBeTranferedThisPass/This->Media->BlockSize;
  936. if (BlockCount > 1) {
  937. Status = DmaBlocks (This, Lba, Buffer, BlockCount, OperationType);
  938. } else {
  939. //Transfer a block worth of data.
  940. Status = TransferBlock (This, Lba, Buffer, OperationType);
  941. }
  942. if (EFI_ERROR(Status)) {
  943. DEBUG ((EFI_D_ERROR, "TransferBlockData fails. %x\n", Status));
  944. goto DoneRestoreTPL;
  945. }
  946. BytesRemainingToBeTransfered -= BytesToBeTranferedThisPass;
  947. Lba += BlockCount;
  948. Buffer = (UINT8 *)Buffer + This->Media->BlockSize;
  949. }
  950. DoneRestoreTPL:
  951. gBS->RestoreTPL (OldTpl);
  952. Done:
  953. return Status;
  954. }
  955. /**
  956. Reset the Block Device.
  957. @param This Indicates a pointer to the calling context.
  958. @param ExtendedVerification Driver may perform diagnostics on reset.
  959. @retval EFI_SUCCESS The device was reset.
  960. @retval EFI_DEVICE_ERROR The device is not functioning properly and could
  961. not be reset.
  962. **/
  963. EFI_STATUS
  964. EFIAPI
  965. MMCHSReset (
  966. IN EFI_BLOCK_IO_PROTOCOL *This,
  967. IN BOOLEAN ExtendedVerification
  968. )
  969. {
  970. return EFI_SUCCESS;
  971. }
  972. /**
  973. Read BufferSize bytes from Lba into Buffer.
  974. @param This Indicates a pointer to the calling context.
  975. @param MediaId Id of the media, changes every time the media is replaced.
  976. @param Lba The starting Logical Block Address to read from
  977. @param BufferSize Size of Buffer, must be a multiple of device block size.
  978. @param Buffer A pointer to the destination buffer for the data. The caller is
  979. responsible for either having implicit or explicit ownership of the buffer.
  980. @retval EFI_SUCCESS The data was read correctly from the device.
  981. @retval EFI_DEVICE_ERROR The device reported an error while performing the read.
  982. @retval EFI_NO_MEDIA There is no media in the device.
  983. @retval EFI_MEDIA_CHANGED The MediaId does not matched the current device.
  984. @retval EFI_BAD_BUFFER_SIZE The Buffer was not a multiple of the block size of the device.
  985. @retval EFI_INVALID_PARAMETER The read request contains LBAs that are not valid,
  986. or the buffer is not on proper alignment.
  987. EFI_STATUS
  988. **/
  989. EFI_STATUS
  990. EFIAPI
  991. MMCHSReadBlocks (
  992. IN EFI_BLOCK_IO_PROTOCOL *This,
  993. IN UINT32 MediaId,
  994. IN EFI_LBA Lba,
  995. IN UINTN BufferSize,
  996. OUT VOID *Buffer
  997. )
  998. {
  999. EFI_STATUS Status;
  1000. //Perform Read operation.
  1001. Status = SdReadWrite (This, (UINTN)Lba, Buffer, BufferSize, READ);
  1002. return Status;
  1003. }
  1004. /**
  1005. Write BufferSize bytes from Lba into Buffer.
  1006. @param This Indicates a pointer to the calling context.
  1007. @param MediaId The media ID that the write request is for.
  1008. @param Lba The starting logical block address to be written. The caller is
  1009. responsible for writing to only legitimate locations.
  1010. @param BufferSize Size of Buffer, must be a multiple of device block size.
  1011. @param Buffer A pointer to the source buffer for the data.
  1012. @retval EFI_SUCCESS The data was written correctly to the device.
  1013. @retval EFI_WRITE_PROTECTED The device can not be written to.
  1014. @retval EFI_DEVICE_ERROR The device reported an error while performing the write.
  1015. @retval EFI_NO_MEDIA There is no media in the device.
  1016. @retval EFI_MEDIA_CHNAGED The MediaId does not matched the current device.
  1017. @retval EFI_BAD_BUFFER_SIZE The Buffer was not a multiple of the block size of the device.
  1018. @retval EFI_INVALID_PARAMETER The write request contains LBAs that are not valid,
  1019. or the buffer is not on proper alignment.
  1020. **/
  1021. EFI_STATUS
  1022. EFIAPI
  1023. MMCHSWriteBlocks (
  1024. IN EFI_BLOCK_IO_PROTOCOL *This,
  1025. IN UINT32 MediaId,
  1026. IN EFI_LBA Lba,
  1027. IN UINTN BufferSize,
  1028. IN VOID *Buffer
  1029. )
  1030. {
  1031. EFI_STATUS Status;
  1032. //Perform write operation.
  1033. Status = SdReadWrite (This, (UINTN)Lba, Buffer, BufferSize, WRITE);
  1034. return Status;
  1035. }
  1036. /**
  1037. Flush the Block Device.
  1038. @param This Indicates a pointer to the calling context.
  1039. @retval EFI_SUCCESS All outstanding data was written to the device
  1040. @retval EFI_DEVICE_ERROR The device reported an error while writting back the data
  1041. @retval EFI_NO_MEDIA There is no media in the device.
  1042. **/
  1043. EFI_STATUS
  1044. EFIAPI
  1045. MMCHSFlushBlocks (
  1046. IN EFI_BLOCK_IO_PROTOCOL *This
  1047. )
  1048. {
  1049. return EFI_SUCCESS;
  1050. }
  1051. EFI_BLOCK_IO_PROTOCOL gBlockIo = {
  1052. EFI_BLOCK_IO_INTERFACE_REVISION, // Revision
  1053. &gMMCHSMedia, // *Media
  1054. MMCHSReset, // Reset
  1055. MMCHSReadBlocks, // ReadBlocks
  1056. MMCHSWriteBlocks, // WriteBlocks
  1057. MMCHSFlushBlocks // FlushBlocks
  1058. };
  1059. /**
  1060. Timer callback to convert card present hardware into a boolean that indicates
  1061. a media change event has happened. If you just check the GPIO you could see
  1062. card 1 and then check again after card 1 was removed and card 2 was inserted
  1063. and you would still see media present. Thus you need the timer tick to catch
  1064. the toggle event.
  1065. @param Event Event whose notification function is being invoked.
  1066. @param Context The pointer to the notification function's context,
  1067. which is implementation-dependent. Not used.
  1068. **/
  1069. VOID
  1070. EFIAPI
  1071. TimerCallback (
  1072. IN EFI_EVENT Event,
  1073. IN VOID *Context
  1074. )
  1075. {
  1076. BOOLEAN Present;
  1077. Present = CardPresent ();
  1078. if (gMMCHSMedia.MediaPresent) {
  1079. if (!Present && !gMediaChange) {
  1080. gMediaChange = TRUE;
  1081. }
  1082. } else {
  1083. if (Present && !gMediaChange) {
  1084. gMediaChange = TRUE;
  1085. }
  1086. }
  1087. }
  1088. EFI_STATUS
  1089. EFIAPI
  1090. MMCHSInitialize (
  1091. IN EFI_HANDLE ImageHandle,
  1092. IN EFI_SYSTEM_TABLE *SystemTable
  1093. )
  1094. {
  1095. EFI_STATUS Status;
  1096. Status = gBS->LocateProtocol (&gEmbeddedExternalDeviceProtocolGuid, NULL, (VOID **)&gTPS65950);
  1097. ASSERT_EFI_ERROR(Status);
  1098. ZeroMem (&gCardInfo, sizeof (CARD_INFO));
  1099. Status = gBS->CreateEvent (EVT_TIMER | EVT_NOTIFY_SIGNAL, TPL_CALLBACK, TimerCallback, NULL, &gTimerEvent);
  1100. ASSERT_EFI_ERROR (Status);
  1101. Status = gBS->SetTimer (gTimerEvent, TimerPeriodic, FixedPcdGet32 (PcdMmchsTimerFreq100NanoSeconds));
  1102. ASSERT_EFI_ERROR (Status);
  1103. //Publish BlockIO.
  1104. Status = gBS->InstallMultipleProtocolInterfaces (
  1105. &ImageHandle,
  1106. &gEfiBlockIoProtocolGuid, &gBlockIo,
  1107. &gEfiDevicePathProtocolGuid, &gMmcHsDevicePath,
  1108. NULL
  1109. );
  1110. return Status;
  1111. }