blob: a35e6be180800347342d2bc10e4da15f937e4a90 [file] [log] [blame]
rjw6c1fd8f2022-11-30 14:33:01 +08001 /*****************************************************************************
2* Copyright Statement:
3* --------------------
4* This software is protected by Copyright and the information contained
5* herein is confidential. The software may not be copied and the information
6* contained herein may not be used or disclosed except with the written
7* permission of MediaTek Inc. (C) 2005
8*
9* BY OPENING THIS FILE, BUYER HEREBY UNEQUIVOCALLY ACKNOWLEDGES AND AGREES
10* THAT THE SOFTWARE/FIRMWARE AND ITS DOCUMENTATIONS ("MEDIATEK SOFTWARE")
11* RECEIVED FROM MEDIATEK AND/OR ITS REPRESENTATIVES ARE PROVIDED TO BUYER ON
12* AN "AS-IS" BASIS ONLY. MEDIATEK EXPRESSLY DISCLAIMS ANY AND ALL WARRANTIES,
13* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE IMPLIED WARRANTIES OF
14* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE OR NONINFRINGEMENT.
15* NEITHER DOES MEDIATEK PROVIDE ANY WARRANTY WHATSOEVER WITH RESPECT TO THE
16* SOFTWARE OF ANY THIRD PARTY WHICH MAY BE USED BY, INCORPORATED IN, OR
17* SUPPLIED WITH THE MEDIATEK SOFTWARE, AND BUYER AGREES TO LOOK ONLY TO SUCH
18* THIRD PARTY FOR ANY WARRANTY CLAIM RELATING THERETO. MEDIATEK SHALL ALSO
19* NOT BE RESPONSIBLE FOR ANY MEDIATEK SOFTWARE RELEASES MADE TO BUYER'S
20* SPECIFICATION OR TO CONFORM TO A PARTICULAR STANDARD OR OPEN FORUM.
21*
22* BUYER'S SOLE AND EXCLUSIVE REMEDY AND MEDIATEK'S ENTIRE AND CUMULATIVE
23* LIABILITY WITH RESPECT TO THE MEDIATEK SOFTWARE RELEASED HEREUNDER WILL BE,
24* AT MEDIATEK'S OPTION, TO REVISE OR REPLACE THE MEDIATEK SOFTWARE AT ISSUE,
25* OR REFUND ANY SOFTWARE LICENSE FEES OR SERVICE CHARGE PAID BY BUYER TO
26* MEDIATEK FOR SUCH MEDIATEK SOFTWARE AT ISSUE.
27*
28* THE TRANSACTION CONTEMPLATED HEREUNDER SHALL BE CONSTRUED IN ACCORDANCE
29* WITH THE LAWS OF THE STATE OF CALIFORNIA, USA, EXCLUDING ITS CONFLICT OF
30* LAWS PRINCIPLES. ANY DISPUTES, CONTROVERSIES OR CLAIMS ARISING THEREOF AND
31* RELATED THERETO SHALL BE SETTLED BY ARBITRATION IN SAN FRANCISCO, CA, UNDER
32* THE RULES OF THE INTERNATIONAL CHAMBER OF COMMERCE (ICC).
33*
34*****************************************************************************/
35
36/*****************************************************************************
37 *
38 * Filename:
39 * ---------
40 * sd.c
41 *
42 * Project:
43 * --------
44 * Maui_Software
45 *
46 * Description:
47 * ------------
48 * driver functons for SD/MMC
49 *
50 *
51 * Author:
52 * -------
53 * -------
54 *
55 *============================================================================
56 * HISTORY
57 * Below this line, this part is controlled by PVCS VM. DO NOT MODIFY!!
58 *------------------------------------------------------------------------------
59 * removed!
60 * removed!
61 * removed!
62 *
63 * removed!
64 * removed!
65 * removed!
66 *
67 * removed!
68 * removed!
69 * removed!
70 *
71 * removed!
72 * removed!
73 * removed!
74 * removed!
75 * removed!
76 *
77 * removed!
78 * removed!
79 * removed!
80 *
81 * removed!
82 * removed!
83 * removed!
84 * removed!
85 *
86 * removed!
87 * removed!
88 * removed!
89 *
90 * removed!
91 * removed!
92 * removed!
93 * removed!
94 * removed!
95 * removed!
96 * removed!
97 *
98 * removed!
99 * removed!
100 * removed!
101 * removed!
102 * removed!
103 * removed!
104 * removed!
105 *
106 * removed!
107 * removed!
108 * removed!
109 * removed!
110 * removed!
111 * removed!
112 *
113 * removed!
114 * removed!
115 * removed!
116 *
117 * removed!
118 * removed!
119 * removed!
120 *
121 * removed!
122 * removed!
123 * removed!
124 * removed!
125 *
126 * removed!
127 * removed!
128 * removed!
129 *
130 * removed!
131 * removed!
132 * removed!
133 *
134 * removed!
135 * removed!
136 * removed!
137 *
138 * removed!
139 * removed!
140 * removed!
141 * removed!
142 *
143 * removed!
144 * removed!
145 * removed!
146 *
147 * removed!
148 * removed!
149 * removed!
150 * removed!
151 * removed!
152 * removed!
153 * removed!
154 * removed!
155 * removed!
156 * removed!
157 * removed!
158 * removed!
159 * removed!
160 * removed!
161 * removed!
162 * removed!
163 * removed!
164 * removed!
165 * removed!
166 * removed!
167 * removed!
168 * removed!
169 * removed!
170 * removed!
171 * removed!
172 * removed!
173 * removed!
174 * removed!
175 * removed!
176 * removed!
177 * removed!
178 * removed!
179 * removed!
180 * removed!
181 * removed!
182 * removed!
183 * removed!
184 * removed!
185 *
186 * removed!
187 * removed!
188 * removed!
189 * removed!
190 * removed!
191 * removed!
192 * removed!
193 * removed!
194 * removed!
195 * removed!
196 * removed!
197 *
198 * removed!
199 * removed!
200 * removed!
201 *
202 * removed!
203 * removed!
204 * removed!
205 *
206 * removed!
207 * removed!
208 * removed!
209 *
210 * removed!
211 * removed!
212 * removed!
213 *
214 * removed!
215 * removed!
216 * removed!
217 *
218 * removed!
219 * removed!
220 * removed!
221 *
222 * removed!
223 * removed!
224 * removed!
225 *
226 * removed!
227 * removed!
228 * removed!
229 *
230 * removed!
231 * removed!
232 * removed!
233 *
234 * removed!
235 * removed!
236 * removed!
237 *
238 * removed!
239 * removed!
240 * removed!
241 *
242 * removed!
243 * removed!
244 * removed!
245 *
246 * removed!
247 * removed!
248 * removed!
249 *
250 * removed!
251 * removed!
252 * removed!
253 *
254 * removed!
255 * removed!
256 * removed!
257 *
258 * removed!
259 * removed!
260 * removed!
261 *
262 * removed!
263 * removed!
264 * removed!
265 *
266 * removed!
267 * removed!
268 * removed!
269 *
270 * removed!
271 * removed!
272 * removed!
273 *
274 * removed!
275 * removed!
276 * removed!
277 *
278 * removed!
279 * removed!
280 * removed!
281 *
282 * removed!
283 * removed!
284 * removed!
285 *
286 * removed!
287 * removed!
288 * removed!
289 *
290 * removed!
291 * removed!
292 * removed!
293 *
294 * removed!
295 * removed!
296 * removed!
297 *
298 * removed!
299 * removed!
300 * removed!
301 *
302 * removed!
303 * removed!
304 * removed!
305 *
306 * removed!
307 * removed!
308 * removed!
309 *
310 * removed!
311 * removed!
312 * removed!
313 *
314 * removed!
315 * removed!
316 * removed!
317 *
318 * removed!
319 * removed!
320 * removed!
321 *
322 * removed!
323 * removed!
324 * removed!
325 *
326 * removed!
327 * removed!
328 * removed!
329 *
330 * removed!
331 * removed!
332 * removed!
333 *
334 * removed!
335 * removed!
336 * removed!
337 *
338 * removed!
339 * removed!
340 * removed!
341 *
342 * removed!
343 * removed!
344 * removed!
345 *
346 * removed!
347 * removed!
348 * removed!
349 *
350 * removed!
351 * removed!
352 * removed!
353 *
354 * removed!
355 * removed!
356 * removed!
357 *
358 * removed!
359 * removed!
360 * removed!
361 *
362 * removed!
363 * removed!
364 * removed!
365 *
366 * removed!
367 * removed!
368 * removed!
369 *
370 * removed!
371 * removed!
372 * removed!
373 *
374 * removed!
375 * removed!
376 * removed!
377 *
378 * removed!
379 * removed!
380 * removed!
381 *
382 * removed!
383 * removed!
384 * removed!
385 *
386 * removed!
387 * removed!
388 * removed!
389 *
390 * removed!
391 * removed!
392 * removed!
393 *
394 * removed!
395 * removed!
396 * removed!
397 *
398 * removed!
399 * removed!
400 * removed!
401 *
402 * removed!
403 * removed!
404 * removed!
405 *
406 * removed!
407 * removed!
408 * removed!
409 *
410 * removed!
411 * removed!
412 * removed!
413 *
414 * removed!
415 * removed!
416 * removed!
417 *
418 * removed!
419 * removed!
420 * removed!
421 *
422 * removed!
423 * removed!
424 * removed!
425 *
426 * removed!
427 * removed!
428 * removed!
429 *
430 * removed!
431 * removed!
432 * removed!
433 *
434 * removed!
435 * removed!
436 * removed!
437 *
438 * removed!
439 * removed!
440 * removed!
441 *
442 * removed!
443 * removed!
444 * removed!
445 *
446 * removed!
447 * removed!
448 * removed!
449 *
450 * removed!
451 * removed!
452 * removed!
453 *
454 * removed!
455 * removed!
456 * removed!
457 *
458 * removed!
459 * removed!
460 * removed!
461 *
462 * removed!
463 * removed!
464 * removed!
465 *
466 * removed!
467 * removed!
468 * removed!
469 *
470 * removed!
471 * removed!
472 * removed!
473 *
474 * removed!
475 * removed!
476 * removed!
477 *
478 * removed!
479 * removed!
480 *
481 *
482 * removed!
483 * removed!
484 *
485 *
486 * removed!
487 * removed!
488 *
489 *
490 * removed!
491 * removed!
492 *
493 *
494 * removed!
495 * removed!
496 *
497 *
498 * removed!
499 * removed!
500 *
501 *
502 * removed!
503 * removed!
504 * removed!
505 *
506 * removed!
507 * removed!
508 *
509 *
510 * removed!
511 * removed!
512 *
513 *
514 * removed!
515 * removed!
516 *
517 *
518 * removed!
519 * removed!
520 *
521 *
522 * removed!
523 * removed!
524 *
525 *
526 * removed!
527 * removed!
528 *
529 *
530 * removed!
531 * removed!
532 *
533 *
534 * removed!
535 * removed!
536 *
537 *
538 * removed!
539 * removed!
540 *
541 *
542 * removed!
543 * removed!
544 *
545 *
546 * removed!
547 * removed!
548 * removed!
549 *
550 * removed!
551 * removed!
552 *
553 *
554 * removed!
555 * removed!
556 *
557 *
558 * removed!
559 * removed!
560 *
561 *
562 * removed!
563 * removed!
564 *
565 *
566 * removed!
567 * removed!
568 *
569 *
570 * removed!
571 * removed!
572 *
573 *
574 * removed!
575 * removed!
576 *
577 *
578 * removed!
579 * removed!
580 *
581 *
582 * removed!
583 * removed!
584 *
585 *
586 * removed!
587 * removed!
588 *
589 *
590 * removed!
591 * removed!
592 *
593 *
594 * removed!
595 * removed!
596 *
597 *
598 * removed!
599 * removed!
600 *
601 *
602 * removed!
603 * removed!
604 *
605 *
606 * removed!
607 * removed!
608 *
609 *
610 * removed!
611 * removed!
612 *
613 *
614 * removed!
615 * removed!
616 *
617 *
618 * removed!
619 * removed!
620 *
621 *
622 * removed!
623 * removed!
624 *
625 *
626 * removed!
627 * removed!
628 *
629 *
630 * removed!
631 * removed!
632 *
633 *
634 * removed!
635 * removed!
636 *
637 *
638 * removed!
639 * removed!
640 *
641 *
642 * removed!
643 * removed!
644 *
645 *
646 * removed!
647 * removed!
648 *
649 *
650 * removed!
651 * removed!
652 *
653 *
654 * removed!
655 * removed!
656 *
657 *
658 * removed!
659 * removed!
660 *
661 *
662 * removed!
663 * removed!
664 *
665 *
666 * removed!
667 * removed!
668 *
669 *
670 * removed!
671 * removed!
672 *
673 *
674 * removed!
675 * removed!
676 *
677 *
678 * removed!
679 * removed!
680 *
681 *
682 * removed!
683 * removed!
684 *
685 *
686 * removed!
687 * removed!
688 *
689 *
690 * removed!
691 * removed!
692 *
693 *
694 * removed!
695 * removed!
696 *
697 *
698 * removed!
699 * removed!
700 *
701 *
702 * removed!
703 * removed!
704 *
705 *
706 * removed!
707 * removed!
708 *
709 *
710 * removed!
711 * removed!
712 *
713 *
714 * removed!
715 * removed!
716 *
717 *
718 * removed!
719 * removed!
720 * removed!
721 *
722 * removed!
723 * removed!
724 *
725 *
726 * removed!
727 * removed!
728 *
729 *
730 * removed!
731 * removed!
732 *
733 *
734 * removed!
735 * removed!
736 *
737 *
738 * removed!
739 * removed!
740 *
741 *
742 * removed!
743 * removed!
744 *
745 *
746 * removed!
747 * removed!
748 *
749 *
750 * removed!
751 * removed!
752 *
753 *
754 * removed!
755 * removed!
756 *
757 *
758 * removed!
759 * removed!
760 *
761 *
762 * removed!
763 * removed!
764 *
765 *
766 * removed!
767 * removed!
768 *
769 *
770 * removed!
771 * removed!
772 *
773 *
774 * removed!
775 * removed!
776 *
777 *
778 * removed!
779 * removed!
780 *
781 *
782 * removed!
783 * removed!
784 *
785 *
786 * removed!
787 * removed!
788 *
789 *
790 * removed!
791 * removed!
792 *
793 *
794 * removed!
795 * removed!
796 *
797 *
798 * removed!
799 * removed!
800 *
801 *
802 * removed!
803 * removed!
804 *
805 *
806 * removed!
807 * removed!
808 *
809 *
810 * removed!
811 * removed!
812 *
813 *
814 * removed!
815 * removed!
816 *
817 *
818 * removed!
819 * removed!
820 *
821 *
822 * removed!
823 * removed!
824 *
825 *
826 * removed!
827 * removed!
828 *
829 *
830 * removed!
831 * removed!
832 *
833 *
834 * removed!
835 * removed!
836 *
837 *
838 * removed!
839 * removed!
840 *
841 *
842 * removed!
843 * removed!
844 *
845 *
846 * removed!
847 * removed!
848 *
849 *
850 * removed!
851 * removed!
852 *
853 *
854 * removed!
855 * removed!
856 *
857 *
858 * removed!
859 * removed!
860 *
861 *
862 * removed!
863 * removed!
864 *
865 *
866 * removed!
867 * removed!
868 *
869 *
870 * removed!
871 * removed!
872 *
873 *
874 * removed!
875 * removed!
876 *
877 *
878 * removed!
879 * removed!
880 *
881 *
882 * removed!
883 * removed!
884 *
885 *
886 * removed!
887 * removed!
888 *
889 *
890 * removed!
891 * removed!
892 *
893 *
894 * removed!
895 * removed!
896 *
897 *
898 * removed!
899 * removed!
900 *
901 *
902 * removed!
903 * removed!
904 *
905 *
906 * removed!
907 * removed!
908 *
909 *
910 * removed!
911 * removed!
912 *
913 *
914 * removed!
915 * removed!
916 *
917 *
918 * removed!
919 * removed!
920 *
921 *
922 * removed!
923 * removed!
924 *
925 *
926 * removed!
927 * removed!
928 *
929 *
930 * removed!
931 * removed!
932 *
933 *
934 * removed!
935 * removed!
936 *
937 *
938 * removed!
939 * removed!
940 *
941 *
942 * removed!
943 * removed!
944 *
945 *
946 * removed!
947 * removed!
948 *
949 *
950 * removed!
951 * removed!
952 *
953 *
954 * removed!
955 * removed!
956 *
957 *
958 * removed!
959 * removed!
960 *
961 *
962 * removed!
963 * removed!
964 *
965 *
966 * removed!
967 * removed!
968 *
969 *
970 * removed!
971 * removed!
972 *
973 *
974 * removed!
975 * removed!
976 *
977 *
978 * removed!
979 * removed!
980 *
981 *
982 * removed!
983 * removed!
984 *
985 *
986 * removed!
987 * removed!
988 *
989 *
990 * removed!
991 * removed!
992 * removed!
993 *
994 * removed!
995 * removed!
996 * removed!
997 *
998 * removed!
999 * removed!
1000 * removed!
1001 *
1002 * removed!
1003 * removed!
1004 * removed!
1005 *
1006 * removed!
1007 * removed!
1008 * removed!
1009 *
1010 * removed!
1011 * removed!
1012 * removed!
1013 *
1014 * removed!
1015 * removed!
1016 * removed!
1017 *
1018 * removed!
1019 * removed!
1020 * removed!
1021 * removed!
1022 *
1023 * removed!
1024 * removed!
1025 * removed!
1026 *
1027 * removed!
1028 * removed!
1029 * removed!
1030 * removed!
1031 * removed!
1032 *
1033 * removed!
1034 * removed!
1035 * removed!
1036 *
1037 * removed!
1038 * removed!
1039 * removed!
1040 *
1041 * removed!
1042 * removed!
1043 * removed!
1044 *
1045 * removed!
1046 * removed!
1047 * removed!
1048 *
1049 * removed!
1050 * removed!
1051 *
1052 * removed!
1053 * removed!
1054 * removed!
1055 *
1056 * removed!
1057 * removed!
1058 * removed!
1059 * removed!
1060 *
1061 * removed!
1062 * removed!
1063 * removed!
1064 *
1065 * removed!
1066 * removed!
1067 * removed!
1068 *
1069 * removed!
1070 * removed!
1071 * removed!
1072 *
1073 * removed!
1074 * removed!
1075 * removed!
1076 *
1077 * removed!
1078 * removed!
1079 * removed!
1080 *
1081 * removed!
1082 * removed!
1083 *
1084 * removed!
1085 * removed!
1086 * removed!
1087 *
1088 * removed!
1089 * removed!
1090 * removed!
1091 * removed!
1092 *
1093 * removed!
1094 * removed!
1095 * removed!
1096 *
1097 *------------------------------------------------------------------------------
1098 * Upper this line, this part is controlled by PVCS VM. DO NOT MODIFY!!
1099 *============================================================================
1100 ****************************************************************************/
1101#include "drv_features.h"
1102#ifndef DRV_MSDC_OFF
1103#include "kal_public_api.h" //MSBB change #include "kal_release.h"
1104
1105#include "kal_general_types.h"
1106//#include "btif_sw.h"
1107//#include "kal_public_api.h"
1108#include "kal_public_defs.h"
1109#include "kal_debug.h"
1110#include "init.h"
1111
1112#include "kal_trace.h"
1113#include "dcl.h"
1114#include "drv_comm.h"
1115#include "drv_features.h"
1116#include "kal_public_defs.h" //MSBB change #include "stack_config.h"
1117#include "qmu_bm.h"
1118#include "qmu_bm_util.h"
1119
1120#if !defined(__UBL__) || defined(__CARD_DOWNLOAD__) || defined(__EMMC_BOOTING__)
1121#include "us_timer.h"
1122#include "msdc_reg_adap.h"
1123#include "reg_base.h"
1124#include "msdc_api.h"
1125#include "msdc_def.h"
1126#include "sd_def.h"
1127#include "upll_ctrl.h"
1128#include "drv_trc.h"
1129#if defined(__AUDIO_DSP_LOWPOWER__)
1130#include "audlp_exp.h"
1131#endif
1132
1133#if defined(__EMMC_BOOTING__)
1134#include "FTL.h"
1135#endif
1136
1137#ifdef DRV_LSD
1138#include "msdc_lsd.h"
1139
1140
1141
1142extern void LSD_Host74TCMDHigh(void);
1143extern kal_bool LSD_HostDetectBusy(void);
1144#endif
1145
1146#if defined(__MSDC_SD_MMC__)
1147//global variables
1148T_SDC_HANDLE gSD_blk[SD_NUM];
1149T_SDC_HANDLE *gSD = gSD_blk;
1150
1151/*global veriable ,operation by DMA ,alloc in uncached memory*/
1152#ifdef MSDC_GPD_BD_BUF_CACHED
1153msdc_gpd_t MSDC_gpd[SD_NUM];
1154msdc_gpd_t MSDC_gpd_end[SD_NUM];
1155
1156msdc_bd_t MSDC_bd[SD_NUM][MSDC_BD_MAX];
1157#else
1158__attribute__ ( (section ("NONCACHEDRW")))msdc_gpd_t MSDC_gpd[SD_NUM];
1159__attribute__ ( (section ("NONCACHEDRW")))msdc_gpd_t MSDC_gpd_end[SD_NUM];
1160
1161__attribute__ ( (section ("NONCACHEDRW")))msdc_bd_t MSDC_bd[SD_NUM][MSDC_BD_MAX];
1162#endif
1163
1164//static SDC_CMD_STATUS gblSDsta;
1165
1166extern MSDC_Custom_Handle msdc_custom_handle;
1167void SD_Sleep4Wait(kal_int32 sleep_tick);
1168void SD_Use13M_Clock(void);
1169extern kal_uint8 MSDC_GetIOCtrlParam(void);
1170extern kal_bool INT_USBBoot(void);
1171#if defined(DRV_MSDC_LATCH_MT6276_SERIES)
1172extern void MSDC_SetLatchTuning(void);
1173#else
1174extern void MSDC_SetIOCONRegDLT(void);
1175#endif//#if defined(DRV_MSDC_LATCH_MT6276_SERIES)
1176//kal_uint32 sd_writeFailReason; // fix Lint warning
1177#if !defined(DRV_MSDC_LATCH_MT6276_SERIES)
1178void SD_SetRedDlt(kal_uint32 redDlt);
1179#endif//#if !defined(DRV_MSDC_LATCH_MT6276_SERIES)
1180extern void SLA_CustomLogging(kal_char *customJob, kal_int32 saAction);
1181
1182/*#ifdef DRV_MSDC_SDC_V3
1183static kal_uint32 sd_cmd_extra = ((64) << 24); // CTOC = 64
1184#else
1185static kal_uint32 sd_cmd_extra = 0;
1186#endif*/
1187
1188#if defined(__SIM_PLUS__)
1189#if !defined(__CUST_NEW__)
1190kal_char MSDC_GetClockWithoutSIMPlus(void);
1191#endif
1192#endif
1193
1194
1195
1196#ifdef DCL_MSDC_INTERFACE
1197#include "dcl.h"
1198
1199SDC_CMD_STATUS SD_SetCallBack(MSDC_CALLBACK callback1, MSDC_CALLBACK callback2, MSDC_CALLBACK callback3, MSDC_CALLBACK callback4, MSDC_CALLBACK callback5, MSDC_CALLBACK callback6);
1200SDC_CMD_STATUS SD_SetReadTestFlag(kal_uint32 readTestFlag);
1201SDC_CMD_STATUS SD_readTest(void);
1202SDC_CMD_STATUS SD_SetUpllClock(void);
1203
1204#ifdef __MEUT__
1205SDDriver_t sd_driver_MTK1 =
1206{
1207 (DCL_SINGLE_BLK_RD)SD_ReadSingleBlock,
1208 (DCL_MUL_BLK_RD)SD_ReadMultiBlock,
1209 (DCL_SINGLE_BLK_WR)SD_WriteSingleBlock,
1210 (DCL_MUL_BLK_WR)SD_WriteMultiBlock,
1211 (DCL_SD_INITITALIZE)SD_Initialize,
1212 (DCL_SET_PRE_ERASE_CNT)SD_SetPreEraseBlk,
1213 (DCL_SD_SET_CALLBACK)SD_SetCallBack,
1214 (DCL_SET_READ_TEST_FLAG)SD_SetReadTestFlag,
1215 (DCL_SD_READ_TEST)SD_readTest,
1216 (DCL_SD_SET_UPLL_CLOCK_TEST)SD_SetUpllClock,
1217 (DCL_SD_ERASE_BLK)SD_FlushSectors,
1218};
1219#else
1220SDDriver_t sd_driver_MTK1 =
1221{
1222 (DCL_SINGLE_BLK_RD)SD_ReadSingleBlock,
1223 (DCL_MUL_BLK_RD)SD_ReadMultiBlock,
1224 (DCL_SINGLE_BLK_WR)SD_WriteSingleBlock,
1225 (DCL_MUL_BLK_WR)SD_WriteMultiBlock,
1226 (DCL_SD_INITITALIZE)SD_Initialize,
1227 (DCL_SET_PRE_ERASE_CNT)SD_SetPreEraseBlk,
1228 (DCL_SD_SET_CALLBACK)NULL,
1229 (DCL_SET_READ_TEST_FLAG)NULL,
1230 (DCL_SD_READ_TEST)NULL,
1231 (DCL_SD_SET_UPLL_CLOCK_TEST)NULL,
1232 (DCL_SD_ERASE_BLK)SD_FlushSectors,
1233 (DCL_GPD_MUL_BLK_RD)SD_GpdReadMultiBlock,
1234 (DCL_GPD_MUL_BLK_WR)SD_GpdWriteMultiBlock,
1235};
1236#endif
1237
1238#endif
1239
1240#if defined( __MSDC_BASIC_LOAD__) || defined( __MEUT__)
1241#define MSDC_TESTBUFFER_SIZE 512
1242kal_uint32 msdc_testBuffer[(MSDC_TESTBUFFER_SIZE / 4)];
1243kal_uint32 msdc_writeBuffer[(MSDC_TESTBUFFER_SIZE / 4)];
1244
1245#define CMD_DVT_TEST_STATUS 7
1246kal_uint32 msdc_ReadTestFlag;
1247MSDC_CALLBACK msdc_TestCallBack1;
1248MSDC_CALLBACK msdc_TestCallBack2;
1249MSDC_CALLBACK msdc_TestCallBack3;
1250MSDC_CALLBACK msdc_TestCallBack4;
1251MSDC_CALLBACK msdc_TestCallBack5;
1252MSDC_CALLBACK msdc_TestCallBack6;
1253static kal_uint32 sendCmdTimes = 0;
1254#endif
1255
1256#ifdef __CARD_DOWNLOAD__
1257extern kal_bool MSDC_QueryIsPowerControllable(void);
1258extern void MSDC_SetPower(kal_bool enable);
1259#endif
1260
1261
1262
1263
1264/*************************************************************************
1265* FUNCTION
1266* SD_Acmd42
1267*
1268* DESCRIPTION
1269* connect/disconnect the 50K Ohm pull-up resistor on CD/DAT3
1270*
1271* PARAMETERS
1272*
1273* RETURNS
1274* SDC_CMD_STATUS
1275*
1276* GLOBALS AFFECTED
1277* gSD
1278*
1279* NOTE
1280*
1281*
1282*************************************************************************/
1283
1284// Get CID(CMD2)
1285SDC_CMD_STATUS SD_Acmd42(kal_bool connect)
1286{
1287 SDC_CMD_STATUS status;
1288 MSDC_DEBUG("[SD][%s %d]send cmd55\r\n",__FUNCTION__,__LINE__);
1289
1290 // send APP_CMD
1291 if ((status = SD_Cmd55(gSD->mRCA)) != NO_ERROR)
1292 return status;
1293
1294 MSDC_DEBUG("[SD][%s %d]send acmd42\r\n",__FUNCTION__,__LINE__);
1295
1296 // send cmd6
1297 if ((status = SD_SendCmd(SDC_CMD_ACMD42, connect,MSDC_CMD_TIMEOUT)) != NO_ERROR)
1298 return status;
1299
1300 //read R1
1301 if ((status = SD_CheckStatus()) != NO_ERROR)
1302 return status;
1303
1304 gSD->mCD_DAT3 = KAL_FALSE; // pull-up resistor is disconnected for data trnasfer
1305 return NO_ERROR;
1306}
1307
1308
1309#if defined(MSDC_MMC441_SUPPORT)
1310
1311kal_bool SD_eMMC_ECSD_setValue(kal_uint8 addr, kal_uint8 value)
1312{
1313 //kal_uint32 r0; // [TODO]: eMMC
1314 //kal_bool status = KAL_FALSE;
1315 kal_uint8 *pData;
1316
1317 if (192 <= addr) //addr above 192 is information registers, we can't write these registers
1318 ASSERT(0);
1319
1320 MSDC_PDNControl(KAL_FALSE);
1321
1322 if (NO_ERROR != SD_Switch_MMC40(SET_BYTE, addr, value, 0))
1323 ASSERT(0);
1324
1325 //if(NO_ERROR != SD_GetStatus(gSD->mRCA,(kal_uint32*)&r0))
1326 // ASSERT(0);
1327 if (NO_ERROR != SD_SendEXTCSD_MMC40(MSDC_Sector))
1328 ASSERT(0);
1329
1330 pData = (kal_uint8 *)MSDC_Sector;
1331
1332 if (value != *(pData + addr))
1333 ASSERT(0);
1334
1335 //status = KAL_TRUE;
1336 MSDC_PDNControl(KAL_TRUE);
1337 return KAL_TRUE;
1338}
1339
1340/*
1341 This API is to ask eMMC to start the partition.
1342 That is, this API should be called after configuring partition settings.
1343*/
1344kal_bool SD_eMMC_ECSD_StartPartition()
1345{
1346 kal_bool status;
1347
1348 /*if this is not eMMC 4.4, assert it */
1349 //EMMC44_CHECK_AND_ASSERT;
1350
1351 /*the device has been partitioned*/
1352 if (EMMC_MASK_PARTITION_SETTING & gSD->mCSD.ext_csd->partition_settig)
1353 {
1354 ASSERT(0);
1355 }
1356
1357 status = SD_eMMC_ECSD_setValue(EXT_CSD_PARTITION_CONFIG_INDEX, 1);
1358
1359 return status;
1360}
1361
1362// unit: 512-byte
1363kal_uint32 SD_eMMC_getWpgSize()
1364{
1365 if ((1 & gSD->mCSD.ext_csd->erase_grp_def) && (gSD->mCSD.ext_csd->hc_wp_grp_size > 0))
1366 return 1024 * gSD->mCSD.ext_csd->hc_erase_grp_size * gSD->mCSD.ext_csd->hc_wp_grp_size;
1367 else
1368 return (gSD->mCSD.wp_grp_size_mmc >> 9);
1369}
1370
1371/*
1372 This API is called to configure partition settings. Size unit is 512-byte.
1373*/
1374kal_bool SD_eMMC_ECSD_configPartition(eMMC_partitions partition, kal_uint32 startAddr, kal_uint32 size, kal_bool isEnhanced)
1375{
1376
1377 kal_bool status;
1378 kal_uint32 maxEnhSizeMult;
1379 kal_uint32 wpgSize;
1380 kal_uint32 wpgNum;
1381 kal_uint32 partitionSize[5];
1382 kal_uint8 regIndex;
1383 kal_uint8 value[3];
1384
1385 if (eMMC_GP_partition1 > partition || eMMC_user_Area < partition)
1386 ASSERT(0);
1387
1388 /*if this is not eMMC 4.4, assert it */
1389 //EMMC44_CHECK_AND_ASSERT;
1390
1391 /*1st, if this card does not support enhanced feature or does not support partition feature, we can not do this function*/
1392
1393 /* 2nd, there is a limitation for the total size of enhanced memory area.
1394 we have to know the total size of other existed enhanced area and check whether the setting violet the limitation.
1395 */
1396 maxEnhSizeMult = gSD->mCSD.ext_csd->max_enh_size_mult[0] | ( gSD->mCSD.ext_csd->max_enh_size_mult[1] << 8) | ( gSD->mCSD.ext_csd->max_enh_size_mult[2] << 16);
1397
1398 /*get current all partition size*/
1399 partitionSize[eMMC_GP_partition1 - eMMC_GP_partition1] = gSD->mCSD.ext_csd->gp_size_mult[0] | ( gSD->mCSD.ext_csd->gp_size_mult[1] << 8) | ( gSD->mCSD.ext_csd->gp_size_mult[2] << 16);
1400 partitionSize[eMMC_GP_partition2 - eMMC_GP_partition1] = gSD->mCSD.ext_csd->gp_size_mult[3] | ( gSD->mCSD.ext_csd->gp_size_mult[4] << 8) | ( gSD->mCSD.ext_csd->gp_size_mult[5] << 16);
1401 partitionSize[eMMC_GP_partition3 - eMMC_GP_partition1] = gSD->mCSD.ext_csd->gp_size_mult[6] | ( gSD->mCSD.ext_csd->gp_size_mult[7] << 8) | ( gSD->mCSD.ext_csd->gp_size_mult[8] << 16);
1402 partitionSize[eMMC_GP_partition4 - eMMC_GP_partition1] = gSD->mCSD.ext_csd->gp_size_mult[9] | ( gSD->mCSD.ext_csd->gp_size_mult[10] << 8) | ( gSD->mCSD.ext_csd->gp_size_mult[11] << 16);
1403 partitionSize[eMMC_user_Area - eMMC_GP_partition1] = gSD->mCSD.ext_csd->enh_size_mult[0] | ( gSD->mCSD.ext_csd->enh_size_mult[1] << 8) | ( gSD->mCSD.ext_csd->enh_size_mult[2] << 16);
1404
1405 /*calculate how many wpg we need to set*/
1406 wpgSize = SD_eMMC_getWpgSize();
1407 wpgNum = (size / wpgSize) + ((size % wpgSize) > 0 ? 1 : 0);
1408
1409 /*replace old size with the new size we want to set*/
1410 partitionSize [partition - eMMC_GP_partition1] = wpgNum;
1411
1412 if ((partitionSize[0] + partitionSize[1] + partitionSize[2] + partitionSize[3] + partitionSize[4]) > maxEnhSizeMult)
1413 return KAL_FALSE;
1414
1415 /*everything check passed, now we can set the value*/
1416 if (eMMC_user_Area > partition)
1417 regIndex = EXT_CSD_GP_SIZE_MULT_GP0_INDEX + 3 * (partition - eMMC_GP_partition1);
1418 else
1419 regIndex = EXT_CSD_ENH_SIZE_MULT_INDEX;
1420
1421 value[2] = wpgNum / 64;
1422 value[1] = (wpgNum - (value[2] * 64)) / 8;
1423 value[0] = wpgNum - (value[2] * 64) - (value[1] * 8);
1424 status = SD_eMMC_ECSD_setValue(regIndex, value[0]);
1425
1426 if (KAL_TRUE != status)
1427 goto err_exit;
1428
1429 status = SD_eMMC_ECSD_setValue(regIndex + 1, value[1]);
1430
1431 if (KAL_TRUE != status)
1432 goto err_exit;
1433
1434 status = SD_eMMC_ECSD_setValue(regIndex + 2, value[2]);
1435
1436 if (KAL_TRUE != status)
1437 goto err_exit;
1438
1439err_exit:
1440 return status;
1441
1442}
1443
1444/*
1445 This API is to configure to boot from specified partition.
1446 By this API, DA can decide from wich partition, will card output the boot code in boot mode.
1447*/
1448kal_bool SD_eMMC_ECSD_setCurrentPart(eMMC_partitions partition)
1449{
1450 kal_uint8 regValue;
1451 kal_bool status;
1452 eMMC_partitions pt;
1453
1454 if (0 == partition || eMMC_user_Area < partition)
1455 ASSERT(0);
1456
1457 /*if this is not eMMC 4.4, assert it */
1458 //EMMC44_CHECK_AND_ASSERT;
1459
1460 pt = (partition == eMMC_user_Area) ? 0 : partition;
1461
1462 regValue = gSD->mCSD.ext_csd->partition_config;
1463
1464 /*currently it uses the setting DA want, no need to change*/
1465 if (pt == (EMMC_MASK_PARTITION_CONFIG & regValue))
1466 return KAL_TRUE;
1467
1468 regValue &= ~EMMC_MASK_PARTITION_CONFIG;
1469 regValue |= pt;
1470 status = SD_eMMC_ECSD_setValue(EXT_CSD_PARTITION_CONFIG_INDEX, regValue);
1471
1472#if 0
1473/* under construction !*/
1474/* under construction !*/
1475/* under construction !*/
1476/* under construction !*/
1477/* under construction !*/
1478/* under construction !*/
1479#if defined(__EMMC_BOOTING__)
1480/* under construction !*/
1481#endif
1482/* under construction !*/
1483/* under construction !*/
1484/* under construction !*/
1485/* under construction !*/
1486/* under construction !*/
1487/* under construction !*/
1488#endif
1489
1490 return status;
1491}
1492
1493/*************************************************************************
1494* FUNCTION
1495* SD_IsEMMC
1496*
1497* DESCRIPTION
1498* Check inserted card is e-MMC 4.4
1499*
1500* PARAMETERS
1501*
1502* RETURNS
1503*
1504* GLOBALS AFFECTED
1505* gSD
1506*
1507*************************************************************************/
1508void SD_IsEmmcV44()
1509{
1510 /* from eMMC 4.3, EXT_CSD_REV has maximum value 3, and from eMMC 4.4, EXT_CSD_REV new value 4, 5
1511 */
1512 if (3 < gSD->mCSD.ext_csd->ext_csd_rev)
1513 {
1514 if (0 != gSD->mCSD.ext_csd->boot_size_mul) //has boot partition, this is eMMC
1515 {
1516 gSD->emmc_info.isEmmcV44 = (kal_bool)KAL_TRUE;
1517 gSD->emmc_info.bootPartitionSize = 2 * 128 * gSD->mCSD.ext_csd->boot_size_mul;
1518 gSD->emmc_info.gp1PartitionSize = SD_eMMC_getWpgSize() *
1519 (gSD->mCSD.ext_csd->gp_size_mult[0]
1520 + ( gSD->mCSD.ext_csd->gp_size_mult[1] * 256)
1521 + ( gSD->mCSD.ext_csd->gp_size_mult[2] * 65536));
1522
1523 /*from spec, alternated boot method is mandatory for eMMC4.4*/
1524 if ( 0 == (0x1 & gSD->mCSD.ext_csd->boot_info))
1525 ASSERT(0);
1526
1527 /*we can't use the card that don't have RST signal support*/
1528 if ( 0x2 == (0x3 & gSD->mCSD.ext_csd->rst_function))
1529 ASSERT(0);
1530
1531 if ( 0x1 == (0x1 & gSD->mCSD.ext_csd->partition_support))
1532 gSD->emmc_info.supportPartition = (kal_bool)KAL_TRUE;
1533 else
1534 gSD->emmc_info.supportPartition = (kal_bool)KAL_FALSE;
1535
1536 if ( 0x2 == (0x2 & gSD->mCSD.ext_csd->partition_support))
1537 gSD->emmc_info.supportEnhancedPart = (kal_bool)KAL_TRUE;
1538 else
1539 gSD->emmc_info.supportEnhancedPart = (kal_bool)KAL_FALSE;
1540 }
1541 else //normal mmc card without boot support
1542 {
1543 gSD->emmc_info.isEmmcV44 = (kal_bool)KAL_FALSE;
1544 }
1545 }
1546 else //spec version below or equals to eMMC 4.3
1547 {
1548 gSD->emmc_info.isEmmcV44 = (kal_bool)KAL_FALSE;
1549 }
1550}
1551
1552#endif//defined(MSDC_MMC441_SUPPORT)
1553
1554
1555/*************************************************************************
1556* FUNCTION
1557* SD_SetMMC40_4bit_high_speed
1558*
1559* DESCRIPTION
1560* Check inserted card is SD or MMC
1561*
1562* PARAMETERS
1563*
1564*
1565* RETURNS
1566* SD_CARD or MMC_CARD
1567*
1568* GLOBALS AFFECTED
1569* gMSDC_Handle
1570*
1571*************************************************************************/
1572SDC_CMD_STATUS SD_SetMMC40_bus_high_speed(void)
1573{
1574 kal_uint32 clock, hs;
1575 // kal_uint8 *pData;
1576
1577 #if !defined(__EMMC_BOOTING__)
1578
1579 if (SD_SetBlength(512) != NO_ERROR)
1580 goto err;
1581
1582 #endif
1583
1584 #ifndef MSDC_SPECIAL_MMC_41_CARD
1585
1586 // read the EXT_CSD
1587 if (SD_SendEXTCSD_MMC40(MSDC_Sector) != NO_ERROR)
1588 goto err;
1589
1590 #endif
1591
1592 /*calculate size*/
1593 if (MMC42_CARD == gMSDC_Handle->mMSDC_type)
1594 {
1595 gSD->mCSD.capacity = (kal_uint64)gSD->mCSD.ext_csd->sec_count * 512;
1596 }
1597
1598 #if defined(MSDC_MMC441_SUPPORT)
1599 SD_IsEmmcV44();
1600 #endif
1601
1602 // set high speed
1603 #ifndef MSDC_SPECIAL_MMC_41_CARD
1604
1605 if (gSD->mCSD.ext_csd->card_type & HS_52M)
1606 #endif
1607 {
1608 // should be 52000
1609 clock = 52000000;
1610 //clock = gMSDC_Handle->msdc_clock / 2;
1611
1612 //if (52000000 < clock)
1613 // clock = clock / 2;
1614
1615 hs = 1;
1616 //MSDC_LSD_WriteReg32(MSDC_IOCON,0x010002FF)
1617
1618 MSDC_DEBUG("[MSDC][%s %d]1.Set clock to %d \r\n",__FUNCTION__,__LINE__,clock);
1619 }
1620
1621 #ifndef MSDC_SPECIAL_MMC_41_CARD
1622 else if (gSD->mCSD.ext_csd->card_type & HS_26M)
1623 {
1624 // should be 26000
1625 clock = 26000000;
1626 hs = 1;
1627 }
1628 else
1629 {
1630 clock = 13000000;
1631 hs = 0;
1632 }
1633
1634 #endif
1635
1636 if (hs)
1637 {
1638 //! [TODO]: eMMC
1639 /* select proper power class
1640 if(SD_Switch_MMC40(SET_BYTE,EXT_CSD_POW_CLASS_INDEX,
1641 (gSD->mCSD.ext_csd->pwr_52_360&0xf) ,0) != NO_ERROR)
1642 goto err;
1643 */
1644
1645
1646
1647 /* enable high speed (26M or 52M)*/
1648 if(SD_Switch_MMC40(SET_BYTE,EXT_CSD_HIGH_SPPED_INDEX,EXT_CSD_ENABLE_HIGH_SPEED,0) != NO_ERROR)
1649 goto err;
1650
1651
1652 // latch data at falling edge to cover the card driving capability
1653 // MSDC_LSD_SetBits32(MSDC_CFG,MSDC_CFG_RED);
1654 }
1655
1656 #ifndef DRV_LSD
1657
1658 //#ifndef DRV_MSDC_CLK_SEARCH
1659 //gMSDC_Handle->msdc_clock = MSDC_CLOCK;
1660 MSDC_SetClock(clock,KAL_FALSE);
1661 //#endif
1662 #else
1663 LSD_HostSetClock(LSD_SPEED_52M);
1664 #endif
1665
1666
1667
1668 if (NO_SINGLE_LINE == gMSDC_Handle->trySingleLine)
1669 {
1670 // select bus width
1671 #if defined(MMC40_USE_4BIT_BUS)
1672 // enable 4-bit bus width
1673 if (SD_Switch_MMC40(SET_BYTE, EXT_CSD_BUS_WIDTH_INDEX, BIT_4_MMC40, 0) != NO_ERROR)
1674 goto err;
1675
1676 #ifdef MSDC_SPECIAL_MMC_41_CARD
1677
1678 if (KAL_TRUE == kal_query_systemInit()
1679 || KAL_TRUE == FTL_isPollingMode()
1680 )
1681 {
1682 MSDC_GPTI_BusyWait(2);
1683 }
1684 else
1685 {
1686 kal_sleep_task(4);
1687 }
1688
1689 #endif
1690
1691 MSDC_SetBusWidth(BIT_4W);
1692 gSD->bus_width = 4;
1693 #elif defined(MMC40_USE_8BIT_BUS)
1694
1695 // enable 8-bit bus width
1696 if (SD_Switch_MMC40(SET_BYTE, EXT_CSD_BUS_WIDTH_INDEX, BIT_8_MMC40, 0) != NO_ERROR)
1697 goto err;
1698 MSDC_SetBusWidth(BIT_8W);
1699 gSD->bus_width = 8;
1700 #endif
1701 }
1702 else
1703 {
1704 gMSDC_Handle->trySingleLine&=(~TEMP_SINGLE_LINE);
1705 }
1706
1707 #ifndef MSDC_SPECIAL_MMC_41_CARD
1708
1709 if (SD_SendEXTCSD_MMC40(MSDC_Sector) != NO_ERROR)
1710 goto err;;
1711
1712 #endif
1713
1714 return NO_ERROR;
1715err:
1716
1717 return ERR_MMC_BUS_HS_ERROR;
1718}
1719/*************************************************************************
1720* FUNCTION
1721* SD_CheckSDorMMC
1722*
1723* DESCRIPTION
1724* Check inserted card is SD or MMC
1725*
1726* PARAMETERS
1727*
1728*
1729* RETURNS
1730* SD_CARD or MMC_CARD
1731*
1732* GLOBALS AFFECTED
1733* gMSDC_Handle
1734*
1735*************************************************************************/
1736T_MSDC_CARD SD_CheckSDorMMC()
1737{
1738 SDC_CMD_STATUS status;
1739
1740#if defined(SD_MMC_HIGH_DENSITY_SUPPORT)
1741 SD_Cmd8();
1742#endif
1743 status = SD_Acmd41_SD();
1744
1745 if (status == NO_ERROR)
1746 return gMSDC_Handle->mMSDC_type; // SD_CARD
1747 else
1748 MSDC_ERR("[SD]SD_Acmd41_SD returns error code: %d\r\n", status);
1749
1750 status = SD_Cmd1_MMC();
1751
1752 if (status == NO_ERROR)
1753 return gMSDC_Handle->mMSDC_type; // MMC_CARD
1754 else
1755 MSDC_ERR("[SD]SD_Cmd1_MMC returns error code: %d\r\n", status);
1756
1757 return UNKNOWN_CARD;
1758}
1759
1760/*************************************************************************
1761* FUNCTION
1762* SD_SetDefault
1763*
1764* DESCRIPTION
1765* set default values to gSD
1766*
1767* PARAMETERS
1768*
1769*
1770* RETURNS
1771*
1772* GLOBALS AFFECTED
1773* gSD
1774*
1775*************************************************************************/
1776void SD_SetDefault(void)
1777{
1778 MSDC_LOCK_TAG tempLock;
1779 kal_mem_cpy(&tempLock, &gSD->mSDdrv_lock, sizeof(MSDC_LOCK_TAG));
1780 kal_mem_set(gSD, 0, sizeof(T_SDC_HANDLE));
1781
1782 gSD->mBKLength = 0;
1783 gSD->mRCA = 0;
1784 gSD->mInactive = KAL_FALSE;
1785 gSD->mState = IDLE_STA;
1786 gSD->bus_width = 1;
1787 //gSD->mCD_DAT3 = KAL_TRUE;
1788
1789 kal_mem_cpy(&gSD->mSDdrv_lock, &tempLock, sizeof(MSDC_LOCK_TAG));
1790}
1791
1792void SD_Use24M_Clock(void)
1793{
1794
1795}
1796
1797void SD_Use13M_Clock(void)
1798{
1799
1800}
1801
1802#ifdef DRV_MSDC_CLK_MT6268_SERIES
1803void SD_Use30M_Clock(void)
1804{
1805
1806}
1807
1808void SD_Use45M_Clock(void)
1809{
1810
1811}
1812#endif
1813
1814#ifdef DRV_MSDC_CLK_SEARCH
1815
1816kal_uint32 whenToStop;
1817kal_uint32 stopTimeout = 300;
1818
1819#if !defined(DRV_MSDC_LATCH_MT6276_SERIES)
1820
1821void SD_SetRedDlt(kal_uint32 redDlt)
1822{
1823
1824}
1825#endif//#if !defined(DRV_MSDC_LATCH_MT6276_SERIES)
1826
1827kal_bool sd_DltTestWithClkStopped(kal_uint32 data_adrs)
1828{
1829 return 0;
1830
1831}
1832
1833#if !defined(DRV_MSDC_LATCH_MT6276_SERIES)
1834
1835kal_bool SD_setCLKAndTest(kal_uint32 targetCLK)
1836{
1837 return 0;
1838}
1839
1840
1841kal_uint32 SD_tuneCLK2()
1842{
1843 return 0;
1844}
1845
1846#else//!defined(DRV_MSDC_LATCH_MT6276_SERIES)
1847
1848kal_bool SD_IsClkInRange(kal_uint32 clk)
1849{
1850 return 0;
1851}
1852
1853kal_bool SD_CanCmdBeLatched(void)
1854{
1855 return 0;
1856}
1857
1858/*kal_bool SD_CanDataBeLatched(msdc_clk_setting cs)
1859{
1860
1861}*/
1862
1863/*SDC_CMD_STATUS MSDC_AutoCalibrate(
1864 msdc_acb_mode mode,
1865 msdc_acb_scan_mode scanMode,
1866 msdc_acb_tun_scheme tunScheme,
1867 kal_uint8 tunBlockNum
1868)
1869{
1870
1871}*/
1872
1873/*kal_uint32 MSDC_ManuCalibrate(
1874 msdc_clk_setting cs,
1875 msdc_acb_mode mode
1876)
1877{
1878
1879}*/
1880
1881#define MAX_NUM_MULTI_PHASE 32
1882SDC_CMD_STATUS FindMostConsecutiveBits(
1883 kal_uint32 word,
1884 kal_uint8 wordLen,
1885 kal_uint8 threshold,
1886 kal_uint8 *pos
1887)
1888{
1889 return 0;
1890}
1891
1892/*SDC_CMD_STATUS MSDC_AutoCalibrate_FindBestLatchWindow(
1893 msdc_acb_scan_mode scanMode,
1894 kal_uint8 *pos
1895)
1896{
1897
1898}*/
1899
1900/*SDC_CMD_STATUS MSDC_ManuCali_FindBestLatchWindow(
1901 msdc_clk_setting cs,
1902 kal_uint32 phaseArraySeamless,
1903 kal_uint8 *pos
1904)
1905{
1906
1907}*/
1908
1909/*kal_uint32 SD_ClkTuning_AutoCalibrate(msdc_clk_setting cs)
1910{
1911
1912}*/
1913
1914/*kal_uint32 SD_ClkTuning_ManualCalibrate(msdc_clk_setting cs)
1915{
1916
1917}*/
1918
1919/*kal_uint32 SD_ClkTuning_FeedbackClk(msdc_clk_setting cs)
1920{
1921
1922}*/
1923
1924kal_uint32 SD_tuneCLK2()
1925{
1926 return 0;
1927}
1928
1929#endif//!defined(DRV_MSDC_LATCH_MT6276_SERIES)
1930
1931#endif//#ifdef DRV_MSDC_CLK_SEARCH
1932
1933#ifdef __MEUT__
1934kal_bool msdcOddNumberSizeTestByDMA;
1935kal_bool msdcDoNotRST;
1936SDC_CMD_STATUS msdcReadTest(kal_uint32 size, kal_uint8 *compareBuffer, kal_uint32 data_adrs)
1937{
1938
1939 return 0;
1940}
1941
1942#endif
1943
1944
1945#ifdef __MSDC_BASIC_LOAD__
1946
1947kal_bool msdcOddNumberSizeTestByDMA;
1948kal_bool msdcDoNotRST;
1949SDC_CMD_STATUS msdcTransferLengthTest(kal_uint32 size, kal_uint8 *compareBuffer, kal_uint32 data_adrs)
1950{
1951 return 0;
1952 }
1953
1954SDC_CMD_STATUS msdcWriteLengthTest(kal_uint32 size, kal_uint8 *compareBuffer, kal_uint32 data_adrs, kal_bool notChange)
1955{
1956 return 0;
1957
1958}
1959#endif
1960
1961#if defined(MSDC_QMU_ENABLE)
1962#define MSDC_QBM_BPS_NUM 1
1963#define MSDC_QBM_BPS_BUF_SZ QBM_QUEUE_GET_MEM_SIZE(QBM_SIZE_TGPD_BPS, MSDC_QBM_BPS_NUM)
1964kal_uint8 msdc_bps_buf[MSDC_QBM_BPS_BUF_SZ];
1965void *g_p_msdc_bps[MSDC_QBM_BPS_NUM];
1966
1967/* Initialize the QUM buffer for MSDC queue transfer */
1968kal_bool SD_QMU_Init(void)
1969{
1970 kal_bool ret = KAL_TRUE;
1971 unsigned char idx = 0;
1972 bm_queue_config conf;
1973 qbm_gpd *p_cur_gpd = NULL ,*p_head_gpd = NULL , *p_tail_gpd = NULL;
1974
1975 /* Init the BPS pointer */
1976 for (idx = 0; idx < MSDC_QBM_BPS_NUM; idx++)
1977 g_p_msdc_bps[idx] = NULL;
1978
1979 /*initial non-free bypass GPD buffer pool*/
1980 qbm_init_q_config(&conf);
1981 conf.buff_num = MSDC_QBM_BPS_NUM;
1982 conf.p_mem_pool_str = msdc_bps_buf;
1983 conf.p_mem_pool_end = msdc_bps_buf + MSDC_QBM_BPS_BUF_SZ;
1984
1985 /*user must flush the GPD after this non-free init queue*/
1986 if (QBM_ERROR_OK != qbm_init_queue_non_free(QBM_TYPE_TGPD_BPS, &conf , (void **)&p_head_gpd, (void **)&p_tail_gpd)) {
1987 return KAL_FALSE;
1988 }
1989
1990 idx = 0;
1991 p_cur_gpd = p_head_gpd;
1992
1993 do {
1994 qbm_set_non_free(p_cur_gpd);
1995 qbm_set_used(p_cur_gpd);
1996 QBM_DES_CLR_HWO(p_cur_gpd);
1997 QBM_DES_SET_NEXT(p_cur_gpd, NULL);
1998
1999 g_p_msdc_bps[idx] = p_cur_gpd;
2000
2001 /*flush GPD here because qbm_init_queue_non_free don't flush GPD*/
2002 QBM_CACHE_FLUSH(p_cur_gpd, sizeof(qbm_gpd));
2003 idx ++;
2004
2005 /*should consider the bps_ptr array count*/
2006 if ((p_cur_gpd == p_tail_gpd) || (idx >= MSDC_QBM_BPS_NUM)) {
2007 break;
2008 }
2009
2010 p_cur_gpd = p_cur_gpd->p_next;
2011 } while(1);
2012
2013 return ret;
2014}
2015#endif
2016
2017/*************************************************************************
2018* FUNCTION
2019* SD_Initialize
2020*
2021* DESCRIPTION
2022* Initial SD controller and card
2023*
2024* PARAMETERS
2025*
2026*
2027* RETURNS
2028* SDC_CMD_STATUS
2029*
2030* GLOBALS AFFECTED
2031* gSD
2032*
2033*************************************************************************/
2034SDC_CMD_STATUS SD_Initialize(void)
2035{
2036 SDC_CMD_STATUS status;
2037 kal_uint32 cid[4], csd[4], scr[4];
2038 kal_uint32 sd_status[16];
2039 kal_uint16 rca;
2040
2041 /*check if init or not*/
2042 if (gMSDC_Handle->mIsInitialized==KAL_TRUE)
2043 {
2044 return NO_ERROR;
2045 }
2046
2047#if defined(MSDC_MMC441_SUPPORT)
2048 gSD->emmc_info.isEmmcV44 = KAL_FALSE;
2049#endif
2050
2051 /* Re-Init gSD */
2052 kal_mem_set(&gSD->mSCR, 0, sizeof(T_SCR));
2053
2054 /*reset event*/
2055 kal_set_eg_events(gMSDC_Handle->MSDC_Events,0,KAL_AND);
2056
2057 /*reset MSDC*/
2058 MSDC_RESET();
2059
2060 /*may switch to 1.8 last time,we should set signal volt to 3.3v and power cycle*/
2061 gMSDC_Handle->signal_volt=3300;
2062 MSDC_SetSignalPower(KAL_TRUE, gMSDC_Handle->signal_volt);
2063 power_cycle(20);
2064
2065 /* Set INIT clock */
2066 MSDC_SetClock(MSDC_INIT_CLOCK,KAL_FALSE);
2067 /*set to 1 bit data line*/
2068 MSDC_SetBusWidth(BIT_1W);
2069 /*SD_SetDefault*/
2070 SD_SetDefault(); //need check the function !!!!!!
2071 /*set latch tuning*/
2072
2073 /*set IOCON1 */
2074 /*set CARD_CK_PWDN=0 */
2075 MSDC_ClearBits32(MSDC_CFG,MSDC_CFG_CKPDN);
2076 /*enable bus clk*/
2077 MSDC_SetBits32(MSDC_CFG,MSDC_CFG_CKDRV_EN);
2078
2079 /*reset cmd0*/
2080 status=SD_Reset();
2081 SD_INITIALIZE_STATUS_CHECK(); /*need check this function !!!!!!!!!!!!*/
2082 /*checkSDorMMC cmd8 acmd41 cmd1*/
2083 if (SD_CheckSDorMMC() == UNKNOWN_CARD)
2084 {
2085 MSDC_ERR("[SD][%s %d]unknow card\r\n",__FUNCTION__,__LINE__);
2086 SD_TRACE2(TRACE_GROUP_5, MSDC_GENERAL_FAIL, MSDC_DRV_TRC_FILE_SD, __LINE__);
2087 status = ERR_STATUS;
2088 goto err;
2089 }
2090 /*getCID cmd2*/
2091 status = SD_GetCID(cid);
2092 SD_INITIALIZE_STATUS_CHECK();
2093 /*validateRCA cmd3*/
2094 status = SD_ValidateRCA(&rca);
2095 SD_INITIALIZE_STATUS_CHECK();
2096 /*GetCSD cmd9*/
2097 status = SD_GetCSD(gSD->mRCA, csd);
2098 SD_INITIALIZE_STATUS_CHECK();
2099 MSDC_DEBUG("[SD][%s %d]send cmd4\r\n",__FUNCTION__,__LINE__);
2100 /*setSDR cmd4*/
2101 if (gSD->mCSD.dsr_imp){
2102 if ((status = SD_SetDSR()) != NO_ERROR)
2103 {
2104 //dbg_print("6\r\n");
2105 SD_TRACE2(TRACE_GROUP_5, MSDC_GENERAL_FAIL, MSDC_DRV_TRC_FILE_SD, __LINE__);
2106 goto err;
2107 }
2108 }
2109 /*check Write Protected*/
2110#if defined(MSDC_WR_PROT_EN)
2111#if defined(_MSDC_INTERNAL_CD_INT_PIN_)
2112 if(!(MSDC_Reg32(MSDC_PS)&MSDC_PS_WP))
2113 {
2114 //gSD->mWPEnabled=KAL_TRUE;
2115 if (gSD->mWPEnabled!=KAL_TRUE)
2116 gSD->mWPEnabled=KAL_FALSE;
2117 }
2118 else
2119 {
2120 //gSD->mWPEnabled=KAL_FALSE;
2121 gSD->mWPEnabled=KAL_TRUE;
2122 }
2123#else
2124 {
2125 DCL_HANDLE handle;
2126
2127 GPIO_CTRL_READ_T data;
2128
2129 /* when use EINT for card detect,get the status */
2130 handle = DclGPIO_Open(DCL_GPIO, MSDC_WP_GPIO);
2131 DclGPIO_Control(handle, GPIO_CMD_READ, (DCL_CTRL_DATA_T *)&data);
2132
2133 if (data.u1IOData)
2134 gSD->mWPEnabled = KAL_TRUE;
2135 else
2136 gSD->mWPEnabled = KAL_FALSE;
2137
2138 DclGPIO_Close(handle);
2139 }
2140#endif
2141#else /* MSDC_WR_PROT_EN */
2142 gSD->mWPEnabled = KAL_FALSE;
2143#endif
2144
2145 MSDC_CRIT("[SD][%s %d]Card is %s\r\n",__FUNCTION__,__LINE__,
2146 gSD->mWPEnabled ? "WP-ed" : "Not WP-ed");
2147
2148 /*select Card cmd7*/
2149 status = SD_SelectCard(gSD->mRCA);
2150 if (status == CARD_IS_LOCKED)
2151 gSD->mIsLocked = KAL_TRUE;
2152 SD_INITIALIZE_STATUS_CHECK();
2153
2154
2155 /*read SCR cmd16 acmd51*/
2156 if (gMSDC_Handle->mMSDC_type==SD_CARD\
2157 ||gMSDC_Handle->mMSDC_type==SD20_HCS_CARD ||gMSDC_Handle->mMSDC_type==SD20_LCS_CARD\
2158 ||gMSDC_Handle->mMSDC_type==SD30_CARD)
2159 {
2160 status = SD_ReadSCR(scr);
2161 SD_INITIALIZE_STATUS_CHECK();
2162
2163 status = SD_ReadSDStatus(sd_status);
2164 SD_INITIALIZE_STATUS_CHECK();
2165
2166 /*set bus width acmd6*/
2167 if (NO_SINGLE_LINE == gMSDC_Handle->trySingleLine)
2168 {
2169 status = SD_SetBusWidth(BIT_4W);
2170 SD_INITIALIZE_STATUS_CHECK();
2171 }
2172 else
2173 {
2174 gMSDC_Handle->trySingleLine&=~(TEMP_SINGLE_LINE);
2175 }
2176
2177 /*acmd42*/
2178 #if !defined(__MSDC_TFLASH_DAT3_1BIT_HOT_PLUG__)
2179 status = SD_Acmd42(KAL_FALSE);
2180 SD_INITIALIZE_STATUS_CHECK();
2181 #endif
2182
2183 status=SD_SwitchSpeedMode();
2184 SD_INITIALIZE_STATUS_CHECK();
2185
2186#if defined(MSDC_CONFIG_SD30_SUPPORT)
2187 if (gMSDC_Handle->mMSDC_type==SD30_CARD)
2188 {
2189
2190 switch (gSD->function_set.function1)
2191 {
2192 case FUN1_SET_SDR104:
2193 MSDC_SetClock(208000000,KAL_FALSE);
2194 gMSDC_Handle->msdc_clkTuneUpperBund = 100000000;
2195 break;
2196 case FUN1_SET_SDR50:
2197 MSDC_SetClock(100000000,KAL_FALSE);
2198 gMSDC_Handle->msdc_clkTuneUpperBund = 50000000;
2199 break;
2200 case FUN1_SET_SDR25_HS:
2201 MSDC_SetClock(50000000,KAL_FALSE);
2202 gMSDC_Handle->msdc_clkTuneUpperBund = 25000000;
2203 break;
2204 case FUN1_SET_SDR12_DS:
2205 MSDC_SetClock(25000000,KAL_FALSE);
2206 gMSDC_Handle->msdc_clkTuneUpperBund = 12500000;
2207 break;
2208 case FUN1_SET_DDR50:
2209 MSDC_SetClock(50000000,KAL_TRUE);
2210 gMSDC_Handle->msdc_clkTuneUpperBund = 25000000;
2211 break;
2212 }
2213 }
2214 else
2215#endif
2216 {
2217 if (gSD->function_set.function1==1)
2218 {
2219 MSDC_CRIT("[SD][%s %d]set Bus Clock to 50M(HS)\r\n",__FUNCTION__,__LINE__);
2220 MSDC_SetClock(50000000,KAL_FALSE);
2221 gMSDC_Handle->msdc_clkTuneUpperBund = 25000000;
2222 }
2223 else
2224 {
2225 MSDC_CRIT("[SD][%s %d]set Bus Clock to 25M(DS)\r\n",__FUNCTION__,__LINE__);
2226 MSDC_SetClock(25000000,KAL_FALSE);
2227 gMSDC_Handle->msdc_clkTuneUpperBund = 12500000;
2228 }
2229 }
2230
2231 /* For SDA compliance test */
2232 if (((gSD->mSCR.spec_ver==SD_SPEC_101)||(gSD->mSCR.spec_ver==SD_SPEC_110)||(gSD->mCSD.csd_ver==CSD_VER_1_0))&&
2233 ((kal_uint32)(gSD->mCSD.capacity / (1024 * 1024)) > 2048)&&(status==NO_ERROR)) {
2234 status = ERR_STATUS;
2235 MSDC_ERR("[SD] We would not mount >2G Card which is compliant to SD1.x\r\n");
2236 goto err;
2237 }
2238 if (((gSD->mSCR.spec_ver<=SD_SPEC_200))&&
2239 ((kal_uint32)(gSD->mCSD.capacity / (1024 * 1024)) > 32768)&&(status==NO_ERROR)) {
2240 status = ERR_STATUS;
2241 MSDC_ERR("[SD] We would not mount >32GB Card which is compliant to SD2.0\r\n");
2242 goto err;
2243 }
2244 }
2245 else
2246 {
2247 MSDC_CRIT("[SD][%s %d]init mmc \r\n",__FUNCTION__,__LINE__);
2248 //mmc card
2249 if ((gMSDC_Handle->mMSDC_type == MMC_CARD || gMSDC_Handle->mMSDC_type == MMC42_CARD) && gSD->mCSD.spec_ver >= 4)
2250 {
2251 if (gMSDC_Handle->mMSDC_type == MMC_CARD) /*we don't need to change MMC42_CARD to MMC40_CARD*/
2252 gMSDC_Handle->mMSDC_type = MMC40_CARD;
2253 status = SD_SetMMC40_bus_high_speed();
2254 SD_INITIALIZE_STATUS_CHECK();
2255 #if defined(MSDC_MMC441_SUPPORT)
2256 if ( gSD->mCSD.ext_csd->ext_csd_rev >= 5 )
2257 {
2258 // set ERASE_GROUP_DEF[175] before issuing read, write, erase, write protect
2259 status = SD_Switch_MMC40(SET_BYTE, EXT_CSD_ERASE_GRP_DEF, 1 , 0);
2260 SD_INITIALIZE_STATUS_CHECK();
2261 }
2262 #endif
2263 }
2264 else
2265 {
2266 MSDC_SetClock(13000000,KAL_FALSE);
2267 }
2268
2269 }
2270
2271 /* Set block length cmd16 */
2272 status = SD_SetBlength(512);
2273 SD_INITIALIZE_STATUS_CHECK();
2274
2275err:
2276
2277 if (status != NO_ERROR)
2278 {
2279 MSDC_ERR("[SD][%s %d]mount fail %x\r\n",__FUNCTION__,__LINE__,status);
2280 SD_SetDefault();
2281 gMSDC_Handle->mIsInitialized = KAL_FALSE;
2282 gMSDC_Handle->mIsPresent = KAL_FALSE;
2283 MSDC_turnOnVMC(gMSDC_Handle->mIsPresent);
2284 MSDC_SetVddPower(KAL_FALSE, gMSDC_Handle->vdd_volt);
2285 MSDC_PDNControl(KAL_TRUE);
2286 }
2287 else
2288 {
2289 MSDC_CRIT("[SD][%s %d]mount ok %x\r\n",__FUNCTION__,__LINE__,status);
2290 gMSDC_Handle->mIsInitialized = KAL_TRUE;
2291 }
2292
2293 /*reset event*/
2294 kal_set_eg_events(gMSDC_Handle->MSDC_Events, 0, KAL_AND);
2295 return status;
2296
2297}
2298
2299#ifdef __MEUT__
2300SDC_CMD_STATUS SD_SetCallBack(MSDC_CALLBACK callback1, MSDC_CALLBACK callback2, MSDC_CALLBACK callback3, MSDC_CALLBACK callback4, MSDC_CALLBACK callback5, MSDC_CALLBACK callback6)
2301{
2302 return 0;
2303}
2304SDC_CMD_STATUS SD_SetReadTestFlag(kal_uint32 readTestFlag)
2305{
2306 return 0;
2307}
2308SDC_CMD_STATUS SD_readTest(void)
2309{
2310
2311 return 0;
2312}
2313
2314SDC_CMD_STATUS SD_SetUpllClock(void)
2315{
2316
2317 return 0;
2318}
2319#endif
2320
2321
2322void SD_InvertN(kal_uint8 *dest, kal_uint8 *src, kal_uint8 len)
2323{
2324 int i;
2325
2326 for (i = 0; i < len; i++)
2327 *(dest + len - 1 - i) = *(src + i);
2328
2329}
2330/*************************************************************************
2331* FUNCTION
2332* power2
2333*
2334* DESCRIPTION
2335* Calculate the power of 2
2336*
2337* PARAMETERS
2338* num:
2339*
2340* RETURNS
2341* 2^num
2342*
2343* GLOBALS AFFECTED
2344*
2345*************************************************************************/
2346static kal_uint32 power2(kal_uint32 num)
2347{
2348 return 1 << num;
2349}
2350
2351/*************************************************************************
2352* FUNCTION
2353* SD_AnalysisCSD
2354*
2355* DESCRIPTION
2356* Analysis Card Specific Data and store in the member of gSD
2357*
2358* PARAMETERS
2359* csd: input csd for analysis
2360* RETURNS
2361*
2362* GLOBALS AFFECTED
2363* gSD
2364*
2365*************************************************************************/
2366void SD_AnalysisCSD(kal_uint32* csd)
2367{
2368 kal_uint8 *ptr;
2369 kal_uint32 c_mult, c_size;
2370
2371 ptr = (kal_uint8*)csd;
2372 c_mult = c_size = 0;
2373 // these offsets refer to the spec. of SD and MMC
2374 GetBitFieldN((kal_uint8*)&gSD->mCSD.csd_ver, ptr, 126, 2);
2375 GetBitFieldN((kal_uint8*)&gSD->mCSD.tacc, ptr, 112, 8);
2376 GetBitFieldN((kal_uint8*)&gSD->mCSD.nsac, ptr, 104, 8);
2377 GetBitFieldN((kal_uint8*)&gSD->mCSD.tran_speed, ptr, 96, 8);
2378 GetBitFieldN((kal_uint8*)&gSD->mCSD.ccc, ptr, 84, 12);
2379 GetBitFieldN((kal_uint8*)&gSD->mCSD.r_blk_len, ptr, 80, 4);
2380 gSD->mCSD.r_blk_len = power2(gSD->mCSD.r_blk_len);
2381 GetBitFieldN((kal_uint8*)&gSD->mCSD.r_blk_part, ptr, 79, 1);
2382 GetBitFieldN((kal_uint8*)&gSD->mCSD.w_blk_misali, ptr, 78, 1);
2383 GetBitFieldN((kal_uint8*)&gSD->mCSD.r_blk_misali, ptr, 77, 1);
2384 GetBitFieldN((kal_uint8*)&gSD->mCSD.dsr_imp, ptr, 76, 1);
2385 GetBitFieldN((kal_uint8*)&gSD->mCSD.w_blk_part, ptr, 21, 1);
2386 GetBitFieldN((kal_uint8*)&gSD->mCSD.w_blk_len, ptr, 22, 4);
2387 gSD->mCSD.w_blk_len = power2(gSD->mCSD.w_blk_len);
2388 GetBitFieldN((kal_uint8*)&gSD->mCSD.wp_grp_enable, ptr, 31, 1);
2389 GetBitFieldN((kal_uint8*)&gSD->mCSD.temp_wp,ptr,12,1);
2390 GetBitFieldN((kal_uint8*)&gSD->mCSD.perm_wp,ptr,13,1);
2391 if (gSD->mCSD.temp_wp || gSD->mCSD.perm_wp)
2392 gSD->mWPEnabled = KAL_TRUE;
2393
2394 // there are some difference of CSD between SD and MMC
2395 if (gMSDC_Handle->mMSDC_type == MMC_CARD || gMSDC_Handle->mMSDC_type == MMC42_CARD)
2396 {
2397 GetBitFieldN((kal_uint8*)&gSD->mCSD.spec_ver, ptr, 122, 4);
2398 GetBitFieldN((kal_uint8*)&gSD->mCSD.erase_sec_size_mmc, ptr, 42, 5);
2399 gSD->mCSD.erase_sec_size_mmc = (gSD->mCSD.erase_sec_size_mmc + 1) * gSD->mCSD.w_blk_len;
2400 GetBitFieldN((kal_uint8*)&gSD->mCSD.erase_grp_size_mmc, ptr, 37, 5);
2401 gSD->mCSD.erase_grp_size_mmc = (gSD->mCSD.erase_grp_size_mmc + 1) * gSD->mCSD.erase_sec_size_mmc;
2402 GetBitFieldN((kal_uint8*)&gSD->mCSD.wp_grp_size_mmc, ptr, 32, 5);
2403 gSD->mCSD.wp_grp_size_mmc = (gSD->mCSD.wp_grp_size_mmc + 1) * gSD->mCSD.erase_grp_size_mmc;
2404 }
2405 else // SD_CARD
2406 {
2407 if (gSD->mCSD.csd_ver == CSD_VER_2_0)
2408 gSD->mIsBlkAddr = 1;
2409 else
2410 gSD->mIsBlkAddr = 0;
2411
2412 GetBitFieldN((kal_uint8*)&gSD->mCSD.erase_sec_size_sd, ptr, 39, 7);
2413 gSD->mCSD.erase_sec_size_sd += 1;
2414 GetBitFieldN((kal_uint8*)&gSD->mCSD.wp_prg_size_sd, ptr, 32, 7);
2415 gSD->mCSD.wp_prg_size_sd = (gSD->mCSD.wp_prg_size_sd + 1) * gSD->mCSD.erase_sec_size_sd;
2416 GetBitFieldN((kal_uint8*)&gSD->mCSD.erase_blk_en_sd, ptr, 46, 1);
2417 }
2418
2419#if defined(SD_MMC_HIGH_DENSITY_SUPPORT)
2420
2421 if ((gMSDC_Handle->mMSDC_type == SD20_HCS_CARD||\
2422 gMSDC_Handle->mMSDC_type == SD30_CARD) && gSD->mCSD.csd_ver >= SD_CSD_VER_20)
2423 {
2424 GetBitFieldN((kal_uint8*)&c_size, ptr, 48, 22);
2425 gSD->mBKNum = (c_size + 1);
2426 gSD->mCSD.capacity = (kal_uint64)gSD->mBKNum * 512 * 1024;
2427 }
2428 else
2429#endif
2430 {
2431 GetBitFieldN((kal_uint8*)&c_mult, ptr, 47, 3);
2432 c_mult = power2(c_mult + 2);
2433 GetBitFieldN((kal_uint8*)&c_size, ptr, 62, 12);
2434 gSD->mBKNum = (c_size + 1) * c_mult;
2435 gSD->mCSD.capacity = (kal_uint64)(c_size + 1) * (kal_uint64)c_mult * (kal_uint64)gSD->mCSD.r_blk_len;
2436 }
2437 if (!(gSD->mCSD.ccc &CCC_BLOCK_WRITE))
2438 gSD->mWPEnabled = KAL_TRUE; //unsupport write command
2439
2440 MSDC_CRIT("[SD][%s %d]The capacity is %d MB, BLK_ADDR(%d)\r\n", __FUNCTION__, __LINE__,
2441 (kal_uint32)(gSD->mCSD.capacity / (1024 * 1024)), gSD->mIsBlkAddr);
2442}
2443
2444/*************************************************************************
2445* FUNCTION
2446* SD_AnalysisCID
2447*
2448* DESCRIPTION
2449* Analysis Card Identificaton and store in the member of gSD
2450*
2451* PARAMETERS
2452* cid: input of card ID for analysis
2453* RETURNS
2454*
2455* GLOBALS AFFECTED
2456* gSD
2457*
2458*************************************************************************/
2459void SD_AnalysisCID(kal_uint32* cid)
2460{
2461 kal_uint8 i;
2462 kal_uint8* pcid;
2463 pcid = (kal_uint8*)cid;
2464
2465 if (gMSDC_Handle->mMSDC_type == MMC_CARD || MMC42_CARD == gMSDC_Handle->mMSDC_type)
2466 {
2467 GetBitFieldN((kal_uint8*)&gSD->mCID.year, pcid, 8, 4);
2468 gSD->mCID.year += 1997;
2469 GetBitFieldN((kal_uint8*)&gSD->mCID.month, pcid, 12, 4);
2470 GetBitFieldN((kal_uint8*)&gSD->mCID.psn, pcid, 16, 32);
2471 GetBitFieldN((kal_uint8*)&gSD->mCID.prv, pcid, 48, 8);
2472
2473 for (i = 0; i < 6; i++)
2474 gSD->mCID.pnm[i] = *(pcid + 7 + i);
2475
2476 GetBitFieldN((kal_uint8*)&gSD->mCID.oid, pcid, 104, 16);
2477 GetBitFieldN((kal_uint8*)&gSD->mCID.mid, pcid, 120, 8);
2478
2479 // special case handling
2480 {
2481 kal_uint8 pnm[] = {0xFF, 0xFF, 0xFF, 0xFF, 0x36, 0x31};
2482
2483 if (gSD->mCID.mid == 6 && gSD->mCID.oid == 0 &&
2484 !kal_mem_cmp(gSD->mCID.pnm, pnm, 6))
2485 {
2486 gSD->flags |= SD_FLAG_MMC_MRSW_FAIL;
2487 }
2488 }
2489#ifdef __CMMB_CAS_FULL_CARD_SUPPORT__
2490 {
2491 kal_uint8 fullCardPnm[] = {0x55, 0x59, 0x4E, 0x41, 0x49, 0x54};
2492
2493 if (!kal_mem_cmp(gSD->mCID.pnm, fullCardPnm, 6)) /*Tianyu does not provide MID and OID*/
2494 {
2495 SD_setFullCard(KAL_TRUE);
2496 gMSDC_Handle->msdc_clkTuneUpperBund = 15000;
2497 }
2498 else
2499 SD_setFullCard(KAL_FALSE);
2500 }
2501#endif
2502
2503 }
2504 else // SD_CARD
2505 {
2506 gSD->mCID.mid = *(pcid + 15);
2507 gSD->mCID.oid = *(pcid + 13) + 256 * (*(pcid + 14));
2508
2509 for (i = 0; i < 5; i++)
2510 gSD->mCID.pnm[i] = *(pcid + 8 + i);
2511
2512 gSD->mCID.prv = *(pcid + 7);
2513 //gSD->mCID.psn = *(kal_uint32*)(pcid+3);
2514 gSD->mCID.psn = (*(kal_uint32*)(pcid + 4) << 8) | *(pcid + 3);
2515 gSD->mCID.month = (kal_uint8)GET_BIT(*(pcid + 1), 0, BIT_MASK_4);
2516 gSD->mCID.year = GET_BIT(*(pcid + 1), 4, BIT_MASK_4) + 16 * GET_BIT(*(pcid + 2), 0, BIT_MASK_4) + 2000;
2517 }
2518
2519#ifdef MSDC_TRACE_LEVEL1
2520 MD_TRC_MSDC_INFORM_CID(gSD->mCID.mid, gSD->mCID.oid);
2521#endif
2522}
2523
2524/*************************************************************************
2525* FUNCTION
2526* SD_AnalysisSCR
2527*
2528* DESCRIPTION
2529* Analysis SD Card Configuration Register and store in the member of gSD
2530*
2531* PARAMETERS
2532* scr: input of scr for analysis
2533* RETURNS
2534*
2535* GLOBALS AFFECTED
2536* gSD
2537*
2538* NOTE
2539* Only for SD card.
2540*
2541*************************************************************************/
2542void SD_AnalysisSCR(kal_uint32* scr)
2543{
2544 kal_uint8 *pscr;
2545
2546 pscr = (kal_uint8*)scr;
2547 gSD->mSCR.spec_ver = (SD_SPEC)((kal_uint8)GET_BIT(*(pscr), 0, BIT_MASK_4));
2548
2549 if (gSD->mSCR.spec_ver > SD_SPEC_101)
2550 gSD->flags |= SD_FLAG_CMD6_SUPPORT;
2551
2552 gSD->mSCR.dat_after_erase = (kal_uint8)GET_BIT(*(pscr + 1), 7, BIT_MASK_1);
2553 gSD->mSCR.security = (kal_uint8)GET_BIT(*(pscr + 1), 4, BIT_MASK_3);
2554 gSD->mSCR.bus_width = (kal_uint8)GET_BIT(*(pscr + 1), 0, BIT_MASK_4);
2555 gSD->mSCR.cmd_support = (kal_uint8)GET_BIT(*(pscr + 3), 0, BIT_MASK_2);
2556
2557 gSD->mSCR.sd_spec3 = (kal_uint8)GET_BIT(*(pscr + 2), 7, BIT_MASK_1);
2558 if ((gSD->mSCR.spec_ver == SD_SPEC_200) && (gSD->mSCR.sd_spec3))
2559 gSD->mSCR.spec_ver = SD_SPEC_30X;
2560 else
2561 gSD->mSCR.spec_ver = SD_SPEC_200;
2562
2563 MSDC_CRIT("[SD] SD_SPEC(%d) SD_SPEC3(%d) SD_BUS_WIDTH=%d\r\n",
2564 gSD->mSCR.spec_ver, gSD->mSCR.sd_spec3, gSD->mSCR.bus_width);
2565 MSDC_CRIT("[SD] SD_SECU(%d) CMD_SUPP(%d): CMD23(%d), CMD20(%d)\r\n",
2566 gSD->mSCR.security, gSD->mSCR.cmd_support,
2567 (gSD->mSCR.cmd_support >> 1) & 0x1, gSD->mSCR.cmd_support & 0x1);
2568}
2569
2570kal_uint32 SD_CmdPollResp(kal_uint32 * error,kal_uint32 pollTime_ms)
2571{
2572 kal_uint32 status;
2573
2574 if (!MSDC_TIMEOUT_WAIT(MSDC_Reg32(MSDC_INT)&MSDC_CMD_INTS,pollTime_ms))
2575 {
2576 status=MSDC_Reg32(MSDC_INT);
2577 MSDC_WriteReg32(MSDC_INT,(status&MSDC_CMD_INTS));
2578 if (status & MSDC_INT_CMDTMO)
2579 {
2580 MSDC_ERR("[SD][%s %d]CMDTMO(%d)\r\n",__FUNCTION__,
2581 __LINE__, gMSDC_Handle->cmd);
2582 *error=ERR_CMD_TIMEOUT;
2583 }
2584 else if (status & MSDC_INT_RSPCRCERR)
2585 {
2586 MSDC_ERR("[SD][%s %d]CMDCRC(%d)\r\n",__FUNCTION__,
2587 __LINE__, gMSDC_Handle->cmd);
2588 *error=ERR_CMD_RSPCRCERR;
2589 }
2590 else if (status & MSDC_INT_CMDRDY)
2591 {
2592 *error=NO_ERROR;
2593 }
2594 /*we get the interrupt information*/
2595 return 0;
2596 }
2597 /*polling timeout ,so we need sleep and try wait interrupt*/
2598 return 1; //tiemeout
2599}
2600
2601/*************************************************************************
2602* FUNCTION
2603* SD_WaitCmdRdyOrTo
2604*
2605* DESCRIPTION
2606* Wait until command ready or timeout
2607*
2608* PARAMETERS
2609*
2610* RETURNS
2611* SDC_CMD_STATUS
2612*
2613* GLOBALS AFFECTED
2614*
2615* NOTE
2616* Interrupt driven and polling are both implemented
2617*
2618*************************************************************************/
2619SDC_CMD_STATUS SD_WaitCmdRdyOrTo(void)
2620{
2621 kal_uint32 ret;
2622 kal_uint32 status;
2623 kal_uint32 flag;
2624 /*poll 5 ms first to check response*/
2625 ret=SD_CmdPollResp(&(gMSDC_Handle->error),5);
2626 if (ret)
2627 {
2628 MSDC_START_TIMER(MSDC_CMD_TIMEOUT/10);
2629 /*enable interrupt*/
2630 MSDC_SetBits32(MSDC_INTEN,MSDC_CMD_INTS|MSDC_INT_CDSC);
2631 /*use interrupt handler*/
2632 kal_retrieve_eg_events(gMSDC_Handle->MSDC_Events,EVENT_CMD_DONE,KAL_OR_CONSUME,&flag,KAL_SUSPEND);
2633 /*disable interrupt*/
2634 MSDC_ClearBits32(MSDC_INTEN, MSDC_CMD_INTS);
2635 MSDC_STOP_TIMER();
2636 if (gMSDC_Handle->is_timeout)
2637 {
2638 gMSDC_Handle->error=MSDC_GPT_TIMEOUT_ERR;
2639 }
2640 else
2641 {
2642 status=gMSDC_Handle->msdc_int&MSDC_CMD_INTS;
2643
2644 if (status &MSDC_INT_CMDRDY)
2645 {
2646 gMSDC_Handle->error=NO_ERROR;
2647 }
2648 else if (status& MSDC_INT_CMDTMO)
2649 {
2650 MSDC_ERR("[SD][%s %d]CMDTMO(%d), MSDC_CMD_INTS:%x\r\n",__FUNCTION__,
2651 __LINE__, gMSDC_Handle->cmd, status);
2652 gMSDC_Handle->error=ERR_CMD_TIMEOUT;
2653 }
2654 else if (status & MSDC_INT_RSPCRCERR)
2655 {
2656 MSDC_ERR("[SD][%s %d]CMDCRC(%d), MSDC_CMD_INTS:%x\r\n",__FUNCTION__,
2657 __LINE__, gMSDC_Handle->cmd, status);
2658 gMSDC_Handle->error=ERR_CMD_RSPCRCERR;
2659 }
2660 else
2661 {
2662 MSDC_ERR("[SD][%s %d]ERR(%d), MSDC_CMD_INTS:%x\r\n",__FUNCTION__,
2663 __LINE__, gMSDC_Handle->cmd, status);
2664 gMSDC_Handle->error=ERR_CMD_TIMEOUT;
2665 }
2666 ret=status;
2667 }
2668 }
2669 return gMSDC_Handle->error;
2670}
2671
2672/*************************************************************************
2673* FUNCTION
2674* SD_WaitDatRdyOrTo
2675*
2676* DESCRIPTION
2677* Wait until data ready or timeout ,just for pio read and write
2678*
2679* PARAMETERS
2680*
2681* RETURNS
2682* SDC_CMD_STATUS
2683*
2684* GLOBALS AFFECTED
2685*
2686* NOTE
2687* just polling
2688*
2689*************************************************************************/
2690 SDC_CMD_STATUS SD_WaitDatRdyOrTo(kal_uint32 *buffer,kal_uint32 byte_len,kal_bool isWrite)
2691 {
2692 kal_uint32 intsts;
2693 kal_uint8 * u8ptr;
2694 kal_uint32 * ptr;
2695 ptr=buffer;
2696
2697 gMSDC_Handle->abort=0;
2698 MSDC_SetBits32(MSDC_INTEN,MSDC_INTEN_DATTMO|MSDC_INTEN_DATCRCERR);
2699 if(!isWrite)
2700 {
2701 /*poll to read data from FIFO*/
2702 while(byte_len)
2703 {
2704
2705 if ((byte_len>=MSDC_FIFO_THD)&&(MSDC_RXFIFOCNT()>=MSDC_FIFO_THD)){
2706 int count =MSDC_FIFO_THD>>2;
2707 do{
2708 *ptr++=MSDC_FIFO_READ32();
2709 }while(--count);
2710 byte_len-=MSDC_FIFO_THD;
2711
2712 }
2713 else if ((byte_len<MSDC_FIFO_THD)&&(MSDC_RXFIFOCNT()>=byte_len))
2714 {
2715 while(byte_len>3){
2716 *ptr++=MSDC_FIFO_READ32();
2717 byte_len-=4;
2718 }
2719 u8ptr=(kal_uint8 *)ptr;
2720 while(byte_len){
2721 *u8ptr++=MSDC_FIFO_READ8();
2722 byte_len--;
2723 }
2724 }
2725 if (gMSDC_Handle->abort){
2726 gMSDC_Handle->abort=0;
2727 MSDC_ERR("[SD][%s %d]pio read abort ,byte_len=%d \r\n",__FUNCTION__,__LINE__,byte_len);
2728 break;
2729 }
2730 }
2731 }
2732 else
2733 {
2734 /*poll to write data into FIFO*/
2735 while(byte_len){
2736 if (byte_len >= MSDC_FIFO_SZ){
2737 if (MSDC_TXFIFOCNT()==0){
2738 int count =MSDC_FIFO_SZ>>2;
2739 do {
2740 MSDC_FIFO_WRITE32(*ptr);
2741 ptr++;
2742 }while(--count);
2743 byte_len-=MSDC_FIFO_SZ;
2744 }
2745 }
2746 else if ((byte_len<MSDC_FIFO_SZ)&&(MSDC_TXFIFOCNT()==0)){
2747 while(byte_len){
2748 while(byte_len>3){
2749 MSDC_FIFO_WRITE32(*ptr);
2750 ptr++;
2751 byte_len-=4;
2752 }
2753 u8ptr=(kal_uint8 *)ptr;
2754 while(byte_len){
2755 MSDC_FIFO_WRITE8(*u8ptr);
2756 u8ptr++;
2757 byte_len--;
2758 }
2759 }
2760 }
2761 if (gMSDC_Handle->abort)
2762 {
2763 gMSDC_Handle->abort=0;
2764 MSDC_ERR("[SD][%s %d]pio write abort ,byte_len=%d \r\n",__FUNCTION__,__LINE__,byte_len);
2765 break;
2766 }
2767 }
2768
2769 }
2770
2771 MSDC_ClearBits32(MSDC_INTEN, MSDC_INTEN_DATTMO|MSDC_INTEN_DATCRCERR);
2772 if (byte_len)
2773 goto end;
2774 intsts =MSDC_PollInts(MSDC_INT_XFER_COMPL|MSDC_INT_DATTMO|MSDC_INT_DATCRCERR,100);
2775 MSDC_DEBUG("[SD][%s %d]intsts =%x \r\n",__FUNCTION__,__LINE__,intsts);
2776 MSDC_CLR_FIFO();
2777 if (intsts&MSDC_INT_XFER_COMPL)
2778 {
2779 gMSDC_Handle->error=NO_ERROR;
2780 }
2781 else if (intsts&MSDC_INT_DATCRCERR){
2782 gMSDC_Handle->error=ERR_DAT_CRCERR;
2783 }
2784 else if (intsts&MSDC_INT_DATTMO)
2785 {
2786 gMSDC_Handle->error=ERR_DAT_TIMEOUT;
2787 }
2788end:
2789 if (gMSDC_Handle->error)
2790 {
2791 MSDC_FatalErrorHandle();
2792 }
2793
2794 /*wait busy for write operation*/
2795 if (isWrite)
2796 {
2797 dbg_print("isWrite=%x ,go to MSDC_CheckCardBusy",isWrite);
2798 MSDC_CheckCardBusy(KAL_FALSE,30*1000);
2799 }
2800 return gMSDC_Handle->error;
2801 }
2802
2803/*************************************************************************
2804* FUNCTION
2805* SD_WaitCardNotBusy
2806*
2807* DESCRIPTION
2808* Wait until card is not busy (R1b)
2809*
2810* PARAMETERS
2811*
2812* RETURNS
2813* void
2814*
2815* GLOBALS AFFECTED
2816*
2817* NOTE
2818* Interrupt driven and polling are both implemented
2819*
2820*************************************************************************/
2821extern kal_bool FTL_isPollingMode();
2822kal_uint32 direct_msdc_entry = 0;
2823
2824SDC_CMD_STATUS SD_WaitCardNotBusy(kal_uint32 timeout_ms)
2825{
2826 if(MSDC_TIMEOUT_WAIT((!SD_IS_R1B_BUSY())&&MSDC_Check_Card_Present(),timeout_ms))
2827 {
2828 gMSDC_Handle->error=ERR_CMD_TIMEOUT;
2829 MSDC_ERR("[SD][%s %d]R1B busy timeout ,wait %d ms\r\n",__FUNCTION__,__LINE__,timeout_ms);
2830 return ERR_CMD_TIMEOUT;
2831 }
2832 return NO_ERROR;
2833}
2834
2835/*************************************************************************
2836* FUNCTION
2837* SD_CheckStatus
2838*
2839* DESCRIPTION
2840* Check command status
2841*
2842* PARAMETERS
2843*
2844* RETURNS
2845* SDC_CMD_STATUS
2846*
2847* GLOBALS AFFECTED
2848*
2849* NOTE
2850*
2851*************************************************************************/
2852SDC_CMD_STATUS SD_CheckStatus(void)
2853{
2854 kal_uint32 status;
2855
2856 status= MSDC_Reg32(SDC_RESP0);
2857 if ((status & SDC_CSTA_MASK) == 0 )
2858 return NO_ERROR;
2859
2860 MSDC_ERR("[SD][%s %d]check status<%x>\r\n",__FUNCTION__,__LINE__,status);
2861 if (status & SDC_CARD_IS_LOCKED)
2862 {
2863
2864 return CARD_IS_LOCKED;
2865 }
2866 return ERR_STATUS;
2867
2868}
2869
2870
2871
2872/*************************************************************************
2873* FUNCTION
2874* SD_Send_Cmd
2875*
2876* DESCRIPTION
2877* to launch the command packet to the card
2878*
2879* PARAMETERS
2880* 1. cmd: the content of SDC_CMD register
2881* 2. arg: the argument(if the command need no argument, fill it with 0)
2882*
2883* RETURNS
2884* SDC_CMD_STATUS
2885*
2886* GLOBALS AFFECTED
2887*
2888* NOTE
2889* 1. Check if controller is available before launch any commands
2890* 2. Maybe add check if card is busy (R1b)
2891*************************************************************************/
2892SDC_CMD_STATUS SD_SendCmdOnly( kal_uint32 cmd, kal_uint32 arg,kal_uint32 timeout_ms)
2893{
2894 kal_uint32 retry_count=0;
2895check_busy:
2896 /*wait CMD busy and SDC busy*/
2897 if (cmd == SDC_CMD_CMD12||cmd==SDC_CMD_CMD13)
2898 {
2899 if (MSDC_TIMEOUT_WAIT((!SD_IS_CMD_BUSY()),timeout_ms))
2900 {
2901 gMSDC_Handle->error=ERR_CMD_TIMEOUT;
2902 MSDC_FatalErrorHandle();
2903 MSDC_ERR("[SD][%s %d]wait cmd busy timeout !!,retry %d times\r\n",__FUNCTION__,__LINE__,retry_count);
2904 }
2905 }
2906 else
2907 {
2908 if (MSDC_TIMEOUT_WAIT((!SD_IS_SDC_BUSY()), timeout_ms))
2909 {
2910 gMSDC_Handle->error=ERR_CMD_TIMEOUT;
2911 MSDC_FatalErrorHandle();
2912 MSDC_ERR("[SD][%s %d]wait SDC busy %d ms timeout!!,retry %d times\r\n",__FUNCTION__,__LINE__,timeout_ms,retry_count);
2913 goto retry;
2914 }
2915 }
2916 if (gSD->mBKLength&&(gSD->mBKLength <= 0xfff))
2917 {
2918 cmd|=(gSD->mBKLength<<16);
2919 }
2920
2921 /* If the card supports CMD23, enable AUTOCMD23 function of MSDC */
2922 if (((cmd & 0x3F) == 18) || ((cmd & 0x3F) == 25)) {
2923 if ((gSD->mSCR.cmd_support >> 1) & 0x1)
2924 cmd |= (2 << 28);
2925 }
2926
2927 MSDC_DEBUG("[SD]CMD=%d, arg=%X\r\n", cmd & 0x3F, arg);
2928
2929 /*set argument*/
2930 MSDC_WriteReg32(SDC_ARG,arg);
2931 /*set command*/
2932 MSDC_WriteReg32(SDC_CMD,cmd);
2933 gMSDC_Handle->cmd = (kal_uint8)(cmd & 0x3F);
2934 gMSDC_Handle->error=NO_ERROR;
2935 return gMSDC_Handle->error;
2936
2937retry:
2938 if ((!SD_IS_SDC_BUSY())&&(retry_count<3)){
2939 retry_count++;
2940 goto check_busy;
2941 }
2942 return gMSDC_Handle->error;
2943
2944}
2945
2946#define MSDC_TUNE_CMD_RESP_TA_MAX (8)
2947#define MSDC_TUNE_INT_DAT_LATCH_CK_MAX (8)
2948#define MSDC_TUNE_WCRC_TA_MAX (8)
2949
2950static kal_uint8 fgCMDTuneLargeScale = 1;
2951static kal_uint32 times_large = 0;
2952static kal_uint32 times_small = 0;
2953
2954static kal_uint8 fgWrTuneLargeScale = 1;
2955static kal_uint32 times_large_w = 0;
2956static kal_uint32 times_small_w = 0;
2957
2958static kal_uint8 fgReadTuneLargeScale = 1;
2959static kal_uint32 times_large_r = 0;
2960static kal_uint32 times_small_r = 0;
2961
2962static kal_uint32 msdc_tune_cmd_retry(kal_uint32 cmd, kal_uint32 arg, kal_uint32 timeout_ms)
2963{
2964 kal_uint32 result = ERR_CMD_RSPCRCERR;
2965
2966 /* CMD12 CRCERR should not tune */
2967 if ((cmd & 0x3F) == 12) {
2968 result = NO_ERROR;
2969 goto done;
2970 }
2971
2972 /* Send 'STOP' command to complete 'TRANS' state */
2973 if (MSDC_Reg32(SDC_CMD)&0x1800)
2974 {
2975 /*check if has data phase*/
2976 result=SD_SendCmdOnly(SDC_CMD_CMD12,SDC_NO_ARG,1000);
2977 result=SD_WaitCmdRdyOrTo();
2978 if (result!=NO_ERROR)
2979 goto err;
2980 }
2981
2982 if (gMSDC_Handle->app_cmd)
2983 {
2984 /*for acmd ,we should send cmd55 again*/
2985 result=SD_SendCmdOnly(SDC_CMD_CMD55,gSD->mRCA,1000);
2986 if (result!=NO_ERROR)
2987 goto err;
2988 result=SD_WaitCmdRdyOrTo();
2989 if (result!=NO_ERROR)
2990 goto err;
2991 }
2992
2993 result=SD_SendCmdOnly(cmd,arg,timeout_ms);
2994
2995 if (result!=NO_ERROR)
2996 goto err;
2997
2998 result=SD_WaitCmdRdyOrTo();
2999 if (result==NO_ERROR)
3000 goto done;
3001 if (result != ERR_CMD_RSPCRCERR)
3002 goto err;
3003
3004err:
3005 MSDC_FatalErrorHandle();
3006done:
3007 return result;
3008}
3009
3010kal_uint32 msdc_tune_cmd_large_scale()
3011{
3012 kal_uint32 ret = 0;
3013 kal_uint32 clk_mode, cmd_resp_ta_cntr, r_smpl;
3014
3015 times_large++;
3016
3017 MSDC_GET_FIELD(MSDC_CFG, MSDC_CFG_CKMOD, clk_mode);
3018 MSDC_GET_FIELD(MSDC_PATCH_BIT1, MSDC_CMD_RSP_TA_CNTR, cmd_resp_ta_cntr);
3019 MSDC_GET_FIELD(MSDC_IOCON, MSDC_IOCON_RSPL, r_smpl);
3020
3021 /*
3022 * If MSDC_CFG.CLK_MODE = 1 && Bus_Speed > 100MHz
3023 * that is ultra high speed mode, tune CMD_RESP_TA first
3024 */
3025 if ((clk_mode == 1) || (clk_mode == 2) ||
3026 (gMSDC_Handle->op_clock >= MSDC_TUNE_UHS_SCLK)) {
3027 cmd_resp_ta_cntr++;
3028 MSDC_SET_FIELD(MSDC_PATCH_BIT1, MSDC_CMD_RSP_TA_CNTR,
3029 cmd_resp_ta_cntr & (MSDC_TUNE_CMD_RESP_TA_MAX - 1));
3030
3031 if (cmd_resp_ta_cntr >= MSDC_TUNE_CMD_RESP_TA_MAX) {
3032 r_smpl++;
3033 MSDC_SET_FIELD(MSDC_IOCON, MSDC_IOCON_RSPL, r_smpl % 2);
3034 }
3035 }
3036 else {
3037 /*
3038 * In low speed mode, just tune R_SMPL
3039 * and set MSDC_CMD_RSP_TA_CNTR back to 0
3040 */
3041 r_smpl++;
3042 cmd_resp_ta_cntr = 0;
3043 MSDC_SET_FIELD(MSDC_IOCON, MSDC_IOCON_RSPL, r_smpl % 2);
3044 MSDC_SET_FIELD(MSDC_PATCH_BIT1, MSDC_CMD_RSP_TA_CNTR, cmd_resp_ta_cntr &
3045 (MSDC_TUNE_CMD_RESP_TA_MAX - 1));
3046 }
3047
3048 /* Now all the parameters are set to 0 */
3049 if (r_smpl >= 2)
3050 ret = 1;
3051
3052 MSDC_GET_FIELD(MSDC_CFG, MSDC_CFG_CKMOD, clk_mode);
3053 MSDC_GET_FIELD(MSDC_PATCH_BIT1, MSDC_CMD_RSP_TA_CNTR, cmd_resp_ta_cntr);
3054 MSDC_GET_FIELD(MSDC_IOCON, MSDC_IOCON_RSPL, r_smpl);
3055
3056 MSDC_NOTICE("[SD] <TUNE_CMD_LS><%d> CKMOD=%d, CMD_RSP_TA=%d, R_SMPL=%d\r\n",
3057 times_large, clk_mode, cmd_resp_ta_cntr, r_smpl);
3058
3059 if (ret)
3060 times_large = 0;
3061
3062 return ret;
3063}
3064
3065kal_uint32 msdc_tune_cmd_small_scale()
3066{
3067 kal_uint32 ret = 0;
3068 kal_uint32 cmd_rxdly, clk_mode, cmd_resp_ta_cntr, r_smpl;
3069
3070 times_small++;
3071 MSDC_GET_FIELD(MSDC_CFG, MSDC_CFG_CKMOD, clk_mode);
3072 MSDC_GET_FIELD(MSDC_PATCH_BIT1, MSDC_CMD_RSP_TA_CNTR, cmd_resp_ta_cntr);
3073 MSDC_GET_FIELD(MSDC_IOCON, MSDC_IOCON_RSPL, r_smpl);
3074 MSDC_GET_FIELD(MSDC_PAD_TUNE, MSDC_PAD_TUNE_CMDRDLY, cmd_rxdly);
3075
3076 /* Adjust CMD_RXDLY in PAD macro */
3077 cmd_rxdly++;
3078 MSDC_SET_FIELD(MSDC_PAD_TUNE, MSDC_PAD_TUNE_CMDRDLY, cmd_rxdly & 0x1F);
3079
3080 /* Adjust R_SMPL */
3081 if (cmd_rxdly >= 32) {
3082 r_smpl++;
3083 MSDC_SET_FIELD(MSDC_IOCON, MSDC_IOCON_RSPL, r_smpl % 2);
3084 }
3085
3086 /*
3087 * Adjust CMD_RSP_TA_CNTR
3088 * if MSDC_CFG.CLK_MODE = 1 && Bus_Speed > 100MHz
3089 */
3090 if (r_smpl >= 2) {
3091 if ((clk_mode == 1) || (clk_mode == 2) || (gMSDC_Handle->op_clock >= MSDC_TUNE_UHS_SCLK)) {
3092 cmd_resp_ta_cntr++;
3093 MSDC_SET_FIELD(MSDC_PATCH_BIT1, MSDC_CMD_RSP_TA_CNTR,
3094 cmd_resp_ta_cntr & (MSDC_TUNE_CMD_RESP_TA_MAX - 1));
3095
3096 if (cmd_resp_ta_cntr >= MSDC_TUNE_CMD_RESP_TA_MAX)
3097 ret = 1;
3098 }
3099 else
3100 ret= 1;
3101 }
3102
3103 MSDC_GET_FIELD(MSDC_PATCH_BIT1, MSDC_CMD_RSP_TA_CNTR, cmd_resp_ta_cntr);
3104 MSDC_GET_FIELD(MSDC_IOCON, MSDC_IOCON_RSPL, r_smpl);
3105 MSDC_GET_FIELD(MSDC_PAD_TUNE, MSDC_PAD_TUNE_CMDRDLY, cmd_rxdly);
3106
3107 MSDC_NOTICE("[SD] <TUNE_CMD_SS><%d> CMD_RXDLY=%d, R_SMPL=%d, CMD_RSP_TA=%d\r\n",
3108 times_small, cmd_rxdly, r_smpl, cmd_resp_ta_cntr);
3109
3110 /* Now all the parameters are set to 0 */
3111 if (ret)
3112 times_small = 0;
3113
3114 return ret;
3115}
3116
3117SDC_CMD_STATUS SD_CmdTuneResp(kal_uint32 cmd,kal_uint32 arg,kal_uint32 timeout_ms)
3118{
3119 kal_uint32 result = ERR_CMD_RSPCRCERR;
3120
3121 do {
3122 /* Retry the CMD with error handling */
3123 result = msdc_tune_cmd_retry(cmd, arg, timeout_ms);
3124
3125 if ((result == ERR_CMD_TIMEOUT) ||
3126 (result == NO_ERROR)) {
3127 if (result == NO_ERROR) {
3128 if (times_large)
3129 fgCMDTuneLargeScale = 0;
3130
3131 times_small = 0;
3132 }
3133 goto done;
3134 }
3135
3136 /* Large scale timing tuning */
3137 if (fgCMDTuneLargeScale) {
3138 if (msdc_tune_cmd_large_scale())
3139 fgCMDTuneLargeScale = 0;
3140 }
3141 /* Small scale timing tuning */
3142 else {
3143 if (msdc_tune_cmd_small_scale())
3144 goto done;
3145 }
3146
3147 } while (1);
3148
3149done:
3150 MSDC_CRIT("[SD] <TUNE_CMD%d_DONE>", cmd & 0x3F);
3151 if (result == NO_ERROR)
3152 MSDC_CRIT(" %s\r\n", "PASS");
3153 else if (result == ERR_CMD_RSPCRCERR)
3154 MSDC_CRIT(" %s\r\n", "CRCERR");
3155 else if (result == ERR_CMD_TIMEOUT)
3156 MSDC_CRIT(" %s\r\n", "TIMEOUT");
3157
3158 return result;
3159}
3160
3161SDC_CMD_STATUS SD_SendCmd(kal_uint32 cmd,kal_uint32 arg,kal_uint32 timeout_ms)
3162{
3163 kal_uint32 status;
3164 /*send command */
3165 status = SD_SendCmdOnly(cmd,arg,timeout_ms);
3166 if (status!=NO_ERROR)
3167 {
3168 MSDC_ERR("[SD][%s %d]send cmd %d error \r\n",__FUNCTION__,__LINE__,cmd);
3169 return status;
3170 }
3171 /*wait command complete*/
3172 status=SD_WaitCmdRdyOrTo();
3173 if (status != NO_ERROR)
3174 {
3175 MSDC_FatalErrorHandle();
3176 if (status == ERR_CMD_RSPCRCERR)
3177 {
3178 SD_CmdTuneResp(cmd, arg,timeout_ms);
3179 }
3180 status = gMSDC_Handle->error;
3181
3182 return status;
3183 }
3184 if (cmd== SDC_CMD_CMD55 )
3185 {
3186 gMSDC_Handle->app_cmd=1;
3187 }
3188 else
3189 {
3190 gMSDC_Handle->app_cmd=0;
3191
3192 }
3193 return status;
3194}
3195kal_uint32 SD_PioRead(kal_uint32 * buffer,kal_uint32 num)
3196{
3197 kal_uint32 *ptr=buffer;
3198 kal_uint8 *u8ptr;
3199 kal_uint32 left;
3200 ptr =buffer;
3201 left=num;
3202 while(left)
3203 {
3204 if ((left>=MSDC_FIFO_THD)&&(MSDC_RXFIFOCNT()>=MSDC_FIFO_THD)){
3205 int count =MSDC_FIFO_THD>>2;
3206 do{
3207 *ptr++=MSDC_FIFO_READ32();
3208 }while(--count);
3209 left-=MSDC_FIFO_THD;
3210
3211 }
3212 else if ((left<MSDC_FIFO_THD)&&(MSDC_RXFIFOCNT()>=left))
3213 {
3214 while(left>3){
3215 *ptr++=MSDC_FIFO_READ32();
3216 left-=4;
3217 }
3218 u8ptr=(kal_uint8 *)ptr;
3219 while(left){
3220 *u8ptr++=MSDC_FIFO_READ8();
3221 left--;
3222 }
3223
3224 if (gMSDC_Handle->abort){
3225 gMSDC_Handle->abort=0;
3226 MSDC_ERR("[SD][%s %d]pio read abort!!, num= %d \r\n",__FUNCTION__,__LINE__,num);
3227 goto end;
3228 }
3229 }
3230 }
3231end:
3232 return left;
3233}
3234
3235kal_uint32 SD_PioWrite(kal_uint32 * buffer,kal_uint32 num)
3236{
3237 kal_uint32 * ptr=buffer;
3238 kal_uint8 *u8ptr;
3239 kal_uint32 left;
3240 ptr=buffer;
3241 left=num;
3242 while(left){
3243 if (left >= MSDC_FIFO_SZ){
3244 if (MSDC_TXFIFOCNT()==0){
3245 int count =MSDC_FIFO_SZ>>2;
3246 do {
3247 MSDC_FIFO_WRITE32(*ptr);
3248 ptr++;
3249 }while(--count);
3250 left-=MSDC_FIFO_SZ;
3251 }
3252 }
3253 else if ((left<MSDC_FIFO_SZ)&&(MSDC_TXFIFOCNT()==0)){
3254 while(left){
3255 while(left>3){
3256 MSDC_FIFO_WRITE32(*ptr);
3257 ptr++;
3258 left-=4;
3259 }
3260 u8ptr=(kal_uint8 *)ptr;
3261 while(left){
3262 MSDC_FIFO_WRITE8(*u8ptr);
3263 u8ptr++;
3264 left--;
3265 }
3266 }
3267 }
3268 if (gMSDC_Handle->abort)
3269 {
3270 gMSDC_Handle->abort=0;
3271 MSDC_ERR("[SD][%s %d]pio write abort %d \r\n",__FUNCTION__,__LINE__,num);
3272 goto done;
3273 }
3274 }
3275
3276done:
3277 return left;
3278}
3279
3280#if !defined(MSDC_QMU_ENABLE)
3281static kal_uint8 msdc_cal_checksum(const void *buf,kal_uint32 len)
3282{
3283 kal_uint32 i,sum=0;
3284 kal_char *data=(char*)buf;
3285 for(i=0;i<len;i++)
3286 {
3287 sum+=*data++;
3288 }
3289 return 0xFF-(kal_uint8)sum;
3290}
3291#endif
3292
3293static DCL_STATUS SD_ConfigGpdList(kal_uint32 size)
3294{
3295#if !defined(MSDC_QMU_ENABLE)
3296 kal_uint32 i,buflen,data_count;
3297 kal_uint32 * data_ptr;
3298 kal_uint32 t1;
3299 qbm_gpd* cur_gpd=NULL,*cur_bd=NULL;
3300 msdc_gpd_t *gpd;
3301 msdc_gpd_t *gpd_end;
3302 qbm_gpd *head;
3303 qbm_gpd *tail;
3304 kal_uint8 sel = 0;
3305
3306 #define CONFIG_GPDLIST_TIMEOUT 10000
3307
3308 head = MSDC_Blk[sel].head;
3309 tail = MSDC_Blk[sel].tail;
3310 gpd = MSDC_Blk[sel].gpd;
3311 gpd_end = MSDC_Blk[sel].gpd_end;
3312
3313 gpd->intr =1; /*don't generate DMA_done interrupt*/
3314 gpd->extlen =0; /*ignore cmd,arg etc*/
3315 gpd->hwo =1; /*config hardware owner*/
3316 gpd->bdp =1; /*use buffer descriptor list*/
3317 gpd->ptr =(void*)(&MSDC_bd[sel][0]);
3318 gpd->next =(void*)gpd_end;
3319
3320 #ifdef MSDC_DMA_CHKSUM_EN
3321 gpd->chksum =0;
3322 gpd->chksum =msdc_cal_checksum(gpd,16);
3323 #endif
3324
3325 gpd_end->intr =0; /*don't generate DMA_done interrupt*/
3326 gpd_end->extlen =0; /*ignore cmd,arg etc*/
3327 gpd_end->hwo =0; /*config hardware owner*/
3328 gpd_end->bdp =0; /*use buffer descriptor list*/
3329 gpd_end->ptr =0;
3330 gpd_end->next =NULL;
3331
3332 #ifdef MSDC_DMA_CHKSUM_EN
3333 gpd_end->chksum =0;
3334 gpd_end->chksum =msdc_cal_checksum(gpd_end,16);
3335 #endif
3336
3337 data_count = 0;
3338 t1 = drv_get_current_time();
3339
3340 for (i=0,cur_gpd=head;;cur_gpd=QBM_DES_GET_NEXT(cur_gpd)) {
3341 if (i > MSDC_BD_MAX)
3342 {
3343 MSDC_ERR("[%s %d]qbm_gpd list is to long,only supprot %d object \r\n",__FUNCTION__,__LINE__,MSDC_BD_MAX);
3344 return STATUS_INVALID_ARGUMENT;
3345 }
3346
3347 /* NULL pointer check */
3348 if (cur_gpd == NULL) {
3349 MSDC_ERR("[%s %d]cur_gpd is NULL pointer!\r\n",__FUNCTION__,__LINE__);
3350 return STATUS_INVALID_ARGUMENT;
3351 }
3352
3353 if (QBM_DES_GET_BDP(cur_gpd))
3354 {
3355 // if GPD with BD with data buffer
3356 cur_bd=QBM_DES_GET_DATAPTR(cur_gpd);
3357 while(1)
3358 {
3359 buflen=QBM_DES_GET_DATALEN(cur_bd);
3360 data_ptr=(kal_uint32 *)QBM_DES_GET_DATAPTR(cur_bd);
3361 if ((data_count+buflen)>size)
3362 { //if buffer length is large the secotors we want to transfer
3363 buflen=size-data_count;
3364 data_count=size;
3365 }
3366 else
3367 {
3368 data_count+=buflen;
3369 }
3370 if (buflen)
3371 { // if point to a buffer adress on this BD
3372
3373 if (((cur_gpd==tail)&&(QBM_DES_GET_EOL(cur_bd)))||(data_count==size))
3374 MSDC_bd[sel][i].eol =1;
3375 else
3376 MSDC_bd[sel][i].eol =0;
3377 MSDC_bd[sel][i].next =&MSDC_bd[sel][i+1];
3378 MSDC_bd[sel][i].ptr =data_ptr;
3379 MSDC_bd[sel][i].buflen =buflen;
3380 clean_and_invalidate_dcache(CPU_CACHE_LINE_ALIGN_ADDR((kal_uint32)data_ptr),CPU_CACHE_LINE_ALIGN_LEN((kal_uint32)data_ptr,buflen));
3381 MSDC_bd[sel][i].blkpad =0;
3382 MSDC_bd[sel][i].dwpad =0;
3383 MSDC_bd[sel][i].chksum=0;
3384 MSDC_bd[sel][i].chksum=msdc_cal_checksum(&MSDC_bd[sel][i],16);
3385 i++;
3386 }
3387 if(QBM_DES_GET_EOL(cur_bd))
3388 {
3389 break;
3390 }
3391 cur_bd=QBM_DES_GET_NEXT(cur_bd);
3392 }
3393 }
3394 else
3395 {
3396 // if GPD with data buffer
3397 buflen=QBM_DES_GET_DATALEN(cur_gpd);
3398 //dbg_print("%d buflen=%d\r\n",i,buflen);
3399 data_ptr=(kal_uint32 *)QBM_DES_GET_DATAPTR(cur_gpd);
3400 if ((data_count+buflen)>size)
3401 {
3402 buflen=size-data_count;
3403 data_count=size;
3404 //dbg_print("entry last data_count %d,buflen %d size %d\r\n",data_count,buflen,size);
3405 }
3406 else
3407 {
3408 data_count+=buflen;
3409 }
3410 if (buflen)
3411 {
3412 if (cur_gpd==tail||data_count==size)
3413 MSDC_bd[sel][i].eol =1;
3414 else
3415 MSDC_bd[sel][i].eol =0;
3416 MSDC_bd[sel][i].next =&MSDC_bd[sel][i+1];
3417 MSDC_bd[sel][i].ptr =data_ptr;
3418 MSDC_bd[sel][i].buflen =buflen;
3419
3420 /*
3421 * There is NO need to clean the data cache, which is transfered
3422 * from MSD and USB, because the buffer is directly read or write
3423 * by DMA, CPU are not involved in.
3424 */
3425 #if defined(MSDC_SCAT_BUF_FLUSH) || defined(ATEST_DRV_MSDC)
3426 clean_and_invalidate_dcache(CPU_CACHE_LINE_ALIGN_ADDR((kal_uint32)data_ptr),CPU_CACHE_LINE_ALIGN_LEN((kal_uint32)data_ptr,buflen));
3427 #endif
3428
3429 MSDC_bd[sel][i].blkpad =0;
3430 MSDC_bd[sel][i].dwpad =0;
3431
3432 #ifdef MSDC_DMA_CHKSUM_EN
3433 MSDC_bd[sel][i].chksum=0;
3434 MSDC_bd[sel][i].chksum=msdc_cal_checksum(&MSDC_bd[sel][i], 16);
3435 #endif
3436
3437 i++;
3438 }
3439 }
3440 if (cur_gpd==tail)
3441 break;
3442
3443 }
3444
3445 if (drv_get_duration_ms(t1)>CONFIG_GPDLIST_TIMEOUT)
3446 {
3447 MSDC_INFO("[%s %d]config gpd list timeout\r\n",__FUNCTION__,__LINE__,MSDC_BD_MAX);
3448 return STATUS_INVALID_ARGUMENT;
3449 }
3450
3451 //if data buffer is not enough
3452 if (data_count!=size)
3453 {
3454 MSDC_INFO("[%s %d]data_count %d,size %d\r\n",__FUNCTION__,__LINE__,data_count,size);
3455 return STATUS_INVALID_ARGUMENT;
3456 }
3457
3458 /* Flush the GPD and BD from cache to memory */
3459 #ifdef MSDC_GPD_BD_BUF_CACHED
3460 clean_and_invalidate_dcache(CPU_CACHE_LINE_ALIGN_ADDR((kal_uint32)gpd),
3461 CPU_CACHE_LINE_ALIGN_LEN((kal_uint32)gpd, sizeof(msdc_gpd_t)));
3462 clean_and_invalidate_dcache(CPU_CACHE_LINE_ALIGN_ADDR((kal_uint32)gpd_end),
3463 CPU_CACHE_LINE_ALIGN_LEN((kal_uint32)gpd_end, sizeof(msdc_gpd_t)));
3464 clean_and_invalidate_dcache(CPU_CACHE_LINE_ALIGN_ADDR((kal_uint32)&MSDC_bd[sel][0]),
3465 CPU_CACHE_LINE_ALIGN_LEN((kal_uint32)&MSDC_bd[sel][0], i * sizeof(msdc_bd_t)));
3466 #endif
3467
3468 return STATUS_OK;
3469
3470#else
3471
3472 qbm_gpd *head, *tail, *tail_bak, *p_bps_gpd, *p_cur_gpd;
3473 kal_uint8 sel = 0;
3474
3475 head = MSDC_Blk[sel].head;
3476 tail = MSDC_Blk[sel].tail;
3477 tail_bak = tail;
3478
3479 /* In case of normal transfer */
3480 if (!gMSDC_Handle->f_tuning) {
3481 p_bps_gpd = g_p_msdc_bps[sel];
3482 if (!p_bps_gpd) {
3483 MSDC_ERR("[%s %d]Invalid loacal bypass GPD buffer!\r\n",__FUNCTION__,__LINE__);
3484 return STATUS_FAIL;
3485 }
3486
3487 /* Link the bypass GPD to tail */
3488 qbmt_common_en_q_rx(p_bps_gpd, p_bps_gpd, (void **)&head, (void **)&tail);
3489
3490 /* Set HWO = 1, cause it is cleared by USB QMU */
3491 p_cur_gpd = head;
3492 do {
3493 if (p_cur_gpd == tail_bak)
3494 break;
3495
3496 QBM_DES_SET_HWO(p_cur_gpd);
3497 QBM_CACHE_FLUSH(p_cur_gpd, 2);
3498
3499 p_cur_gpd = p_cur_gpd->p_next;
3500 } while(1);
3501 }
3502 /* In case of re-try on tuning */
3503 else {
3504 p_cur_gpd = head;
3505
3506 /* Re-Set HWO = 1, and flush cache */
3507 do {
3508 QBM_DES_SET_HWO(p_cur_gpd);
3509 QBM_CACHE_FLUSH(p_cur_gpd, sizeof(qbm_gpd));
3510
3511 if ((p_cur_gpd == tail))
3512 break;
3513
3514 p_cur_gpd = p_cur_gpd->p_next;
3515
3516 } while(1);
3517 }
3518
3519 /* Set the QMU start address */
3520 gMSDC_Handle->buf_addr = (void *)MSDC_Blk[sel].head;
3521
3522 return STATUS_OK;
3523
3524#endif
3525}
3526
3527SDC_CMD_STATUS SD_ReqHandleData(kal_uint32 data_adrs, void* buffer, kal_uint32 num,kal_bool isWrite,kal_bool isLinkListBuf)
3528{
3529 kal_uint32 status ;
3530 kal_bool dma;
3531 kal_uint32 intsts;
3532 kal_uint8 cmd23_sup = 0;
3533
3534 MSDC_INFO("[SD]SD_Req: CMD%s Addr=%x BlkNum=%d Buf=%x\r\n",
3535 isWrite ? "25(24)" : "18(17)", data_adrs, num, buffer);
3536
3537 /*Set block size and block num*/
3538 if (gSD->mBKLength!=512)
3539 {
3540 status =SD_SetBlength(512);
3541 if (status != NO_ERROR)
3542 {
3543 return status;
3544 }
3545
3546 }
3547 MSDC_WriteReg32(SDC_BLK_NUM,num);
3548 /*set read timeout*/
3549 /*check we use dma or pio*/
3550 if(gSD->mBKLength*num <512)
3551 {
3552 /*use pio*/
3553 dma=0;
3554 //set to PIO mode
3555 BitFieldWrite32((kal_uint32 *)MSDC_CFG, 1, MSDC_CFG_PIO);
3556 gMSDC_Handle->dma_xfer=0;
3557 }
3558 else
3559 {
3560 /*use dma*/
3561 dma=1;
3562 //set to DMA mode
3563 BitFieldWrite32((kal_uint32 *)MSDC_CFG, 0, MSDC_CFG_PIO);
3564 gMSDC_Handle->dma_xfer=1;
3565 }
3566
3567 dma=1; /*driver unsupport PIO now*/
3568 gMSDC_Handle->dma_xfer=1;
3569 if (dma)
3570 {
3571 kal_set_eg_events(gMSDC_Handle->MSDC_Events, 0,KAL_AND);
3572 /*enable DMA*/
3573 MSDC_ClearBits32(MSDC_CFG,MSDC_CFG_PIO);
3574 /*start command*/
3575 if (!isWrite)
3576 {
3577 if (num==1)
3578 {
3579 status=SD_SendCmdOnly(SDC_CMD_CMD17,data_adrs,MSDC_CMD_TIMEOUT);
3580 }
3581 else
3582 {
3583 status=SD_SendCmdOnly(SDC_CMD_CMD18,data_adrs,MSDC_CMD_TIMEOUT);
3584 }
3585 }
3586 else
3587 {
3588 if (num==1)
3589 {
3590 status=SD_SendCmdOnly(SDC_CMD_CMD24,data_adrs,MSDC_CMD_TIMEOUT);
3591 }
3592 else
3593 {
3594 status=SD_SendCmdOnly(SDC_CMD_CMD25,data_adrs,MSDC_CMD_TIMEOUT);
3595 }
3596 }
3597 if (status !=NO_ERROR)
3598 {
3599 goto done;
3600 }
3601 /*map dma data*/
3602
3603 /*config dma*/
3604 gMSDC_Handle->total_count=num*gSD->mBKLength;
3605 gMSDC_Handle->buf_addr=buffer;
3606
3607 if (isLinkListBuf) {
3608 status = SD_ConfigGpdList(gMSDC_Handle->total_count);
3609 if (status != STATUS_OK) {
3610 MSDC_ERR("[%s %d]Config GPD list fail!\r\n",__FUNCTION__,__LINE__);
3611 return status;
3612 }
3613 }
3614
3615 MSDC_DMATransferFirst(isWrite,isLinkListBuf);
3616
3617 /*wait cmd rsp*/
3618 status=SD_WaitCmdRdyOrTo();
3619 if (status != NO_ERROR)
3620 {
3621 MSDC_FatalErrorHandle();
3622 if (status == ERR_CMD_RSPCRCERR)
3623 {
3624 if (!isWrite)
3625 { if (num==1)
3626 status=SD_CmdTuneResp(SDC_CMD_CMD17, data_adrs,MSDC_CMD_TIMEOUT);
3627 else
3628 status=SD_CmdTuneResp(SDC_CMD_CMD18, data_adrs,MSDC_CMD_TIMEOUT);
3629 }
3630 else
3631 {
3632 if(num==1)
3633 status=SD_CmdTuneResp(SDC_CMD_CMD24, data_adrs,MSDC_CMD_TIMEOUT);
3634 else
3635 status=SD_CmdTuneResp(SDC_CMD_CMD25, data_adrs,MSDC_CMD_TIMEOUT);
3636 }
3637 }
3638 if(status != NO_ERROR)
3639 goto done;
3640 }
3641 /*start dma and wait data complete*/
3642 status = MSDC_DMATransferFinal(isWrite,isLinkListBuf);
3643 }
3644 else
3645 {
3646 /*pio mode*/
3647 if (SD_SendCmd(((isWrite==KAL_TRUE) ?SDC_CMD_CMD25:SDC_CMD_CMD18),data_adrs,MSDC_CMD_TIMEOUT))
3648 {
3649 goto done;
3650 }
3651 MSDC_SetBits32(MSDC_INTEN,MSDC_INTEN_DATTMO|MSDC_INTEN_DATCRCERR);
3652 if(!isWrite)
3653 {
3654 /*poll to read data from FIFO*/
3655 status =SD_PioRead(buffer,num*gSD->mBKLength);
3656 }
3657 else
3658 {
3659 /*poll to write data to FIFO*/
3660 status =SD_PioWrite(buffer,num*gSD->mBKLength);
3661 }
3662
3663 MSDC_ClearBits32(MSDC_INTEN, MSDC_INTEN_DATTMO|MSDC_INTEN_DATCRCERR);
3664 if (status)
3665 {
3666 goto done;
3667 }
3668 intsts =MSDC_PollInts(MSDC_INT_XFER_COMPL|MSDC_INT_DATTMO|MSDC_INT_DATCRCERR,100);
3669 if (intsts&MSDC_INT_XFER_COMPL)
3670 {
3671 status=gMSDC_Handle->error=NO_ERROR;
3672 }
3673 else if (intsts&MSDC_INT_DATCRCERR){
3674 status=gMSDC_Handle->error=ERR_DAT_CRCERR;
3675 }
3676 else if (intsts&MSDC_INT_DATTMO)
3677 {
3678 status=gMSDC_Handle->error=ERR_DAT_TIMEOUT;
3679 }
3680 else
3681 MSDC_ERR("[SD][%s %d]SW timeout in wait PIO data done\r\n",__FUNCTION__,__LINE__);
3682 }
3683done:
3684 if (status)
3685 {
3686 MSDC_FatalErrorHandle();
3687 }
3688
3689 /*cmd12 to stop data*/
3690 cmd23_sup = (gSD->mSCR.cmd_support >> 1) & 0x1;
3691 if (((num>1) && !cmd23_sup) || ((num>1) && cmd23_sup && status))
3692 SD_SendCmd(SDC_CMD_CMD12, SDC_NO_ARG, MSDC_CMD_TIMEOUT);
3693
3694 /* Check card status after each operation */
3695 MSDC_CheckCardBusy(KAL_FALSE, 10*1000);
3696
3697 return status;
3698}
3699
3700kal_uint32 msdc_tune_write_large_scale()
3701{
3702 kal_uint32 ret = 0;
3703 kal_uint32 ultra_hs = 0;
3704 kal_uint32 clk_mode, wr_datcrc_ta, w_d_smpl;
3705
3706 times_large_w++;
3707
3708 MSDC_GET_FIELD(MSDC_CFG, MSDC_CFG_CKMOD, clk_mode);
3709 MSDC_GET_FIELD(MSDC_PATCH_BIT1, MSDC_WRDAT_CRCS_TA_CNTR, wr_datcrc_ta);
3710 MSDC_GET_FIELD(MSDC_IOCON, MSDC_IOCON_WDSPL, w_d_smpl);
3711
3712 /*
3713 * If MSDC_CFG.CLK_MODE = 1 && Bus_Speed > 100MHz
3714 * that is ultra high speed mode, tune WRDAT_CRCS_TA_CNTR first
3715 */
3716 if ((clk_mode == 1) || (clk_mode == 2) || (gMSDC_Handle->op_clock > MSDC_TUNE_UHS_SCLK))
3717 ultra_hs = 1;
3718
3719 if (ultra_hs) {
3720 wr_datcrc_ta++;
3721 MSDC_SET_FIELD(MSDC_PATCH_BIT1, MSDC_WRDAT_CRCS_TA_CNTR,
3722 wr_datcrc_ta & (MSDC_TUNE_WCRC_TA_MAX - 1));
3723
3724 if (wr_datcrc_ta >= MSDC_TUNE_WCRC_TA_MAX) {
3725 w_d_smpl++;
3726 MSDC_SET_FIELD(MSDC_IOCON, MSDC_IOCON_WDSPL, w_d_smpl % 2);
3727 }
3728 }
3729 else {
3730 w_d_smpl++;
3731 wr_datcrc_ta = 0;
3732 MSDC_SET_FIELD(MSDC_IOCON, MSDC_IOCON_WDSPL, w_d_smpl % 2);
3733 MSDC_SET_FIELD(MSDC_PATCH_BIT1, MSDC_WRDAT_CRCS_TA_CNTR,
3734 wr_datcrc_ta & (MSDC_TUNE_WCRC_TA_MAX - 1));
3735 }
3736
3737 if (w_d_smpl >= 2) {
3738 ret = 1;
3739 }
3740
3741 MSDC_GET_FIELD(MSDC_PATCH_BIT1, MSDC_WRDAT_CRCS_TA_CNTR, wr_datcrc_ta);
3742 MSDC_GET_FIELD(MSDC_IOCON, MSDC_IOCON_WDSPL, w_d_smpl);
3743
3744 MSDC_NOTICE("[SD] <TUNE_WR_LS><%d> %s=%d, %s=%d, %s=%d\r\n",
3745 times_large_w, "CKMOD", clk_mode,
3746 "WR_DATCRC_TA", wr_datcrc_ta, "W_D_SMPL", w_d_smpl);
3747
3748 if (ret)
3749 times_large_w = 0;
3750
3751 return ret;
3752}
3753
3754kal_uint32 msdc_tune_write_small_scale()
3755{
3756 kal_uint32 ret = 0;
3757 kal_uint32 ultra_hs = 0;
3758 kal_uint32 clk_mode, wr_datcrc_ta, w_d_smpl, dat0_rd_dly, dat_wr_rxdly;
3759
3760 times_small_w++;
3761
3762 /*
3763 * When re-enter the tuning flow,
3764 * Clear the pad macro then tune from the beginning
3765 */
3766 if (times_small_w == 1) {
3767 MSDC_SET_FIELD(MSDC_PAD_TUNE, MSDC_PAD_TUNE_DATWRDLY, 0);
3768 }
3769
3770 MSDC_GET_FIELD(MSDC_CFG, MSDC_CFG_CKMOD, clk_mode);
3771 MSDC_GET_FIELD(MSDC_PATCH_BIT1, MSDC_WRDAT_CRCS_TA_CNTR, wr_datcrc_ta);
3772 MSDC_GET_FIELD(MSDC_IOCON, MSDC_IOCON_WDSPL, w_d_smpl);
3773 MSDC_GET_FIELD(MSDC_DAT_RDDLY0, MSDC_DAT_RDDLY0_D0, dat0_rd_dly);
3774 MSDC_GET_FIELD(MSDC_PAD_TUNE, MSDC_PAD_TUNE_DATWRDLY, dat_wr_rxdly);
3775
3776 /*
3777 * If MSDC_CFG.CLK_MODE = 1 && Bus_Speed > 100MHz
3778 * that is ultra high speed mode, tune WRDAT_CRCS_TA_CNTR
3779 * and PAT_DAT_WR_RXDLY at last
3780 */
3781 if ((clk_mode == 1) || (clk_mode == 2) || (gMSDC_Handle->op_clock > MSDC_TUNE_UHS_SCLK))
3782 ultra_hs = 1;
3783
3784 dat_wr_rxdly++;
3785 MSDC_SET_FIELD(MSDC_PAD_TUNE, MSDC_PAD_TUNE_DATWRDLY, dat_wr_rxdly & 0x1F);
3786
3787 if (dat_wr_rxdly >= 32) {
3788 w_d_smpl++;
3789 MSDC_SET_FIELD(MSDC_IOCON, MSDC_IOCON_WDSPL, w_d_smpl % 2);
3790 }
3791
3792 if (ultra_hs) {
3793 if (w_d_smpl >= 2) {
3794 wr_datcrc_ta++;
3795 MSDC_SET_FIELD(MSDC_PATCH_BIT1, MSDC_WRDAT_CRCS_TA_CNTR,
3796 wr_datcrc_ta & (MSDC_TUNE_WCRC_TA_MAX - 1));
3797 }
3798
3799 if (wr_datcrc_ta >= MSDC_TUNE_WCRC_TA_MAX)
3800 ret = 1;
3801 }
3802
3803 if (w_d_smpl >= 2)
3804 ret = 1;
3805
3806 MSDC_GET_FIELD(MSDC_PATCH_BIT1, MSDC_WRDAT_CRCS_TA_CNTR, wr_datcrc_ta);
3807 MSDC_GET_FIELD(MSDC_IOCON, MSDC_IOCON_WDSPL, w_d_smpl);
3808 MSDC_GET_FIELD(MSDC_DAT_RDDLY0, MSDC_DAT_RDDLY0_D0, dat0_rd_dly);
3809 MSDC_GET_FIELD(MSDC_PAD_TUNE, MSDC_PAD_TUNE_DATWRDLY, dat_wr_rxdly);
3810
3811 MSDC_NOTICE("[SD] <TUNE_WR_SS><%d> %s=%d, %s=%d, %s=%d\r\n",
3812 times_small_w, "CKMOD", clk_mode,
3813 "WR_DATCRC_TA", wr_datcrc_ta, "W_D_SMPL", w_d_smpl);
3814 MSDC_NOTICE(" %s=%d, %s=%d\r\n",
3815 "DAT0_RD_DLY", dat0_rd_dly, "DAT_WR_RXDLY", dat_wr_rxdly);
3816
3817 if (ret)
3818 times_small_w = 0;
3819
3820 return ret;
3821}
3822
3823kal_uint32 SD_TuneWrite(kal_uint32 address,void * txbuffer,kal_uint32 num,kal_bool isLinkListBuf)
3824{
3825 kal_uint32 result = ERR_DAT_CRCERR;
3826
3827 do {
3828 /* Retry the Write with error handling */
3829 result = SD_ReqHandleData(address,txbuffer,num,KAL_TRUE,isLinkListBuf);
3830
3831 if (/*(result == ERR_DAT_TIMEOUT) ||*/
3832 (result == NO_ERROR)) {
3833 if (times_large_w)
3834 fgWrTuneLargeScale = 0;
3835
3836 times_small_w = 0;
3837
3838 goto done;
3839 }
3840
3841 /* Large scale timing tuning */
3842 if (fgWrTuneLargeScale) {
3843 if (msdc_tune_write_large_scale())
3844 fgWrTuneLargeScale = 0;
3845 }
3846 /* Small scale timing tuning */
3847 else {
3848 if (msdc_tune_write_small_scale())
3849 goto done;
3850 }
3851
3852 } while (1);
3853
3854done:
3855 MSDC_CRIT("[SD] <TUNE_WRITE_DONE>");
3856 if (result == NO_ERROR)
3857 MSDC_CRIT(" %s\r\n", "PASS");
3858 else if (result == ERR_DAT_CRCERR)
3859 MSDC_CRIT(" %s\r\n", "CRCERR");
3860 else if (result == ERR_DAT_TIMEOUT)
3861 MSDC_CRIT(" %s\r\n", "TIMEOUT");
3862
3863 return result;
3864}
3865
3866
3867kal_uint32 msdc_tune_read_large_scale()
3868{
3869 kal_uint32 ret = 0;
3870 kal_uint32 ultra_hs = 0;
3871 kal_uint32 clk_mode, int_dat_latch, ckgen_dly, r_d_smpl;
3872
3873 times_large_r++;
3874
3875 MSDC_GET_FIELD(MSDC_CFG, MSDC_CFG_CKMOD, clk_mode);
3876 MSDC_GET_FIELD(MSDC_PATCH_BIT0, MSDC_INT_DAT_LATCH_CK_SEL, int_dat_latch);
3877 MSDC_GET_FIELD(MSDC_PATCH_BIT0, MSDC_CKGEN_MSDC_DLY_SEL, ckgen_dly);
3878 MSDC_GET_FIELD(MSDC_IOCON, MSDC_IOCON_RDSPL, r_d_smpl);
3879
3880 /*
3881 * If MSDC_CFG.CLK_MODE = 1 && Bus_Speed > 100MHz
3882 * that is ultra high speed mode, tune INT_DAT_LATCH_CK_SEL
3883 * and CKGEN_MSDC_DLY_SEL first
3884 */
3885 if ((clk_mode == 1) || (clk_mode == 2) || (gMSDC_Handle->op_clock > MSDC_TUNE_UHS_SCLK))
3886 ultra_hs = 1;
3887
3888 if (ultra_hs) {
3889 /* Sampling edge is fixed by default setting - rising edge */
3890 int_dat_latch++;
3891 MSDC_SET_FIELD(MSDC_PATCH_BIT0, MSDC_INT_DAT_LATCH_CK_SEL,
3892 int_dat_latch & (MSDC_TUNE_INT_DAT_LATCH_CK_MAX - 1));
3893
3894 if (int_dat_latch >= MSDC_TUNE_INT_DAT_LATCH_CK_MAX) {
3895 ckgen_dly++;
3896 MSDC_SET_FIELD(MSDC_PATCH_BIT0, MSDC_CKGEN_MSDC_DLY_SEL, ckgen_dly & 0x1F);
3897
3898 if (ckgen_dly >= 32)
3899 ret = 1;
3900 }
3901 }
3902 else {
3903 /*
3904 * In low speed mode, just tune R_D_SMPL
3905 * and set other parameters back to 0
3906 */
3907 r_d_smpl++;
3908 int_dat_latch = 0;
3909 ckgen_dly = 0;
3910 MSDC_SET_FIELD(MSDC_IOCON, MSDC_IOCON_RDSPL, r_d_smpl % 2);
3911 MSDC_SET_FIELD(MSDC_PATCH_BIT0, MSDC_INT_DAT_LATCH_CK_SEL,
3912 int_dat_latch & (MSDC_TUNE_INT_DAT_LATCH_CK_MAX - 1));
3913 MSDC_SET_FIELD(MSDC_PATCH_BIT0, MSDC_CKGEN_MSDC_DLY_SEL, ckgen_dly & 0x1F);
3914
3915 }
3916
3917 if (r_d_smpl >= 2)
3918 ret = 1;
3919
3920 MSDC_GET_FIELD(MSDC_PATCH_BIT0, MSDC_INT_DAT_LATCH_CK_SEL, int_dat_latch);
3921 MSDC_GET_FIELD(MSDC_PATCH_BIT0, MSDC_CKGEN_MSDC_DLY_SEL, ckgen_dly);
3922 MSDC_GET_FIELD(MSDC_IOCON, MSDC_IOCON_RDSPL, r_d_smpl);
3923
3924 MSDC_NOTICE("[SD] <TUNE_RD_LS><%d> %s=%d, %s=%d, %s=%d, %s=%d\r\n",
3925 times_large_r, "CKMOD", clk_mode,
3926 "INT_DAT_L", int_dat_latch, "CKGEN_DLY", ckgen_dly,
3927 "R_D_SMPL", r_d_smpl);
3928
3929 if (ret)
3930 times_large_r = 0;
3931
3932 return ret;
3933
3934}
3935
3936kal_uint32 msdc_tune_read_small_scale()
3937{
3938 kal_uint32 ret = 0;
3939 kal_uint32 ultra_hs = 0;
3940 kal_uint32 clk_mode, int_dat_latch, ckgen_dly, r_d_smpl, dat_rddly0, dat_rddly1;
3941 kal_uint32 dat0_rd_dly, dat1_rd_dly, dat2_rd_dly, dat3_rd_dly;
3942 kal_uint32 dat4_rd_dly, dat5_rd_dly, dat6_rd_dly, dat7_rd_dly;
3943
3944 kal_uint32 ddr = 0, dcrc_sts;
3945
3946 times_small_r++;
3947
3948 MSDC_GET_FIELD(MSDC_CFG, MSDC_CFG_CKMOD, clk_mode);
3949
3950 /*
3951 * If MSDC_CFG.CLK_MODE = 1 && Bus_Speed > 100MHz
3952 * that is ultra high speed mode, tune INT_DAT_LATCH_CK_SEL
3953 * and CKGEN_MSDC_DLY_SEL at last
3954 */
3955 if ((clk_mode == 1) || (clk_mode == 2) || (gMSDC_Handle->op_clock > MSDC_TUNE_UHS_SCLK))
3956 ultra_hs = 1;
3957
3958 /*
3959 * When re-enter the tune in Non-UHS mode,
3960 * Clear the pad macro then tune from the beginning
3961 */
3962 if ((times_small_r == 1) && (ultra_hs == 0)) {
3963 MSDC_SET_FIELD(MSDC_IOCON, MSDC_IOCON_RDSPL, 0);
3964 MSDC_WriteReg32(MSDC_DAT_RDDLY0, 0);
3965 MSDC_WriteReg32(MSDC_DAT_RDDLY1, 0);
3966 }
3967
3968 MSDC_GET_FIELD(MSDC_PATCH_BIT0, MSDC_INT_DAT_LATCH_CK_SEL, int_dat_latch);
3969 MSDC_GET_FIELD(MSDC_PATCH_BIT0, MSDC_CKGEN_MSDC_DLY_SEL, ckgen_dly);
3970 MSDC_GET_FIELD(MSDC_IOCON, MSDC_IOCON_RDSPL, r_d_smpl);
3971 dat_rddly0 = MSDC_Reg32(MSDC_DAT_RDDLY0);
3972 dat_rddly1 = MSDC_Reg32(MSDC_DAT_RDDLY1);
3973
3974 /* Get data CRC status */
3975 MSDC_GET_FIELD(SDC_DCRC_STS, SDC_DCRC_STS_NEG | SDC_DCRC_STS_POS, dcrc_sts);
3976
3977 /* Check output clock is SDR mode or DDR mode */
3978 ddr = (clk_mode == 2) ? 1 : 0;
3979 if (!ddr)
3980 dcrc_sts &= ~SDC_DCRC_STS_NEG;
3981
3982 /* Tune PAD macro first */
3983 MSDC_SET_FIELD(MSDC_IOCON, MSDC_IOCON_DDLSEL, 1);
3984
3985 dat0_rd_dly = (dat_rddly0 >> 24) & 0x1F;
3986 dat1_rd_dly = (dat_rddly0 >> 16) & 0x1F;
3987 dat2_rd_dly = (dat_rddly0 >> 8) & 0x1F;
3988 dat3_rd_dly = (dat_rddly0 >> 0) & 0x1F;
3989 dat4_rd_dly = (dat_rddly1 >> 24) & 0x1F;
3990 dat5_rd_dly = (dat_rddly1 >> 16) & 0x1F;
3991 dat6_rd_dly = (dat_rddly1 >> 8) & 0x1F;
3992 dat7_rd_dly = (dat_rddly1 >> 0) & 0x1F;
3993
3994 if (ddr) {
3995 dat0_rd_dly = (dcrc_sts & (1 << 0) || dcrc_sts & (1 << 8)) ? (dat0_rd_dly + 1) : dat0_rd_dly;
3996 dat1_rd_dly = (dcrc_sts & (1 << 1) || dcrc_sts & (1 << 9)) ? (dat1_rd_dly + 1) : dat1_rd_dly;
3997 dat2_rd_dly = (dcrc_sts & (1 << 2) || dcrc_sts & (1 << 10)) ? (dat2_rd_dly + 1) : dat2_rd_dly;
3998 dat3_rd_dly = (dcrc_sts & (1 << 3) || dcrc_sts & (1 << 11)) ? (dat3_rd_dly + 1) : dat3_rd_dly;
3999 dat4_rd_dly = (dcrc_sts & (1 << 4) || dcrc_sts & (1 << 12)) ? (dat4_rd_dly + 1) : dat4_rd_dly;
4000 dat5_rd_dly = (dcrc_sts & (1 << 5) || dcrc_sts & (1 << 13)) ? (dat5_rd_dly + 1) : dat5_rd_dly;
4001 dat6_rd_dly = (dcrc_sts & (1 << 6) || dcrc_sts & (1 << 14)) ? (dat6_rd_dly + 1) : dat6_rd_dly;
4002 dat7_rd_dly = (dcrc_sts & (1 << 7) || dcrc_sts & (1 << 15)) ? (dat7_rd_dly + 1) : dat7_rd_dly;
4003 } else {
4004 dat0_rd_dly = (dcrc_sts & (1 << 0)) ? (dat0_rd_dly + 1) : dat0_rd_dly;
4005 dat1_rd_dly = (dcrc_sts & (1 << 1)) ? (dat1_rd_dly + 1) : dat1_rd_dly;
4006 dat2_rd_dly = (dcrc_sts & (1 << 2)) ? (dat2_rd_dly + 1) : dat2_rd_dly;
4007 dat3_rd_dly = (dcrc_sts & (1 << 3)) ? (dat3_rd_dly + 1) : dat3_rd_dly;
4008 dat4_rd_dly = (dcrc_sts & (1 << 4)) ? (dat4_rd_dly + 1) : dat4_rd_dly;
4009 dat5_rd_dly = (dcrc_sts & (1 << 5)) ? (dat5_rd_dly + 1) : dat5_rd_dly;
4010 dat6_rd_dly = (dcrc_sts & (1 << 6)) ? (dat6_rd_dly + 1) : dat6_rd_dly;
4011 dat7_rd_dly = (dcrc_sts & (1 << 7)) ? (dat7_rd_dly + 1) : dat7_rd_dly;
4012 }
4013
4014 dat_rddly0 = ((dat0_rd_dly & 0x1F) << 24) | ((dat1_rd_dly & 0x1F) << 16) |
4015 ((dat2_rd_dly & 0x1F) << 8) | ((dat3_rd_dly & 0x1F) << 0);
4016 dat_rddly1 = ((dat4_rd_dly & 0x1F) << 24) | ((dat5_rd_dly & 0x1F) << 16) |
4017 ((dat6_rd_dly & 0x1F) << 8) | ((dat7_rd_dly & 0x1F) << 0);
4018
4019 MSDC_WriteReg32(MSDC_DAT_RDDLY0, dat_rddly0);
4020 MSDC_WriteReg32(MSDC_DAT_RDDLY1, dat_rddly1);
4021
4022 /* Then R_D_SMPL */
4023 if( (dat0_rd_dly >= 32) || (dat1_rd_dly >= 32) || (dat2_rd_dly >= 32) || (dat3_rd_dly >= 32)||
4024 (dat4_rd_dly >= 32) || (dat5_rd_dly >= 32) || (dat6_rd_dly >= 32) || (dat7_rd_dly >= 32)){
4025
4026 /*
4027 * On ultra-hs mode, do NOT tune sampling edge,
4028 * because of the 'internal boundary' issue of the current IP
4029 */
4030 if (!ultra_hs) {
4031 r_d_smpl++;
4032 MSDC_SET_FIELD(MSDC_IOCON, MSDC_IOCON_RDSPL, r_d_smpl % 2);
4033 }
4034
4035 /* Re-tune the data pad macro */
4036 MSDC_WriteReg32(MSDC_DAT_RDDLY0, 0);
4037 MSDC_WriteReg32(MSDC_DAT_RDDLY1, 0);
4038
4039 /* Then CKGEN_MSDC_DLY_SEL if it is SDR104 mode */
4040 if (ultra_hs) {
4041 ckgen_dly++;
4042 MSDC_SET_FIELD(MSDC_PATCH_BIT0, MSDC_CKGEN_MSDC_DLY_SEL, ckgen_dly & 0x1F);
4043
4044 if (ckgen_dly >= 32)
4045 ret = 1;
4046 }
4047 else {
4048 if (r_d_smpl >= 2)
4049 ret = 1;
4050 }
4051
4052 }
4053
4054 MSDC_GET_FIELD(MSDC_PATCH_BIT0, MSDC_INT_DAT_LATCH_CK_SEL, int_dat_latch);
4055 MSDC_GET_FIELD(MSDC_PATCH_BIT0, MSDC_CKGEN_MSDC_DLY_SEL, ckgen_dly);
4056 MSDC_GET_FIELD(MSDC_IOCON, MSDC_IOCON_RDSPL, r_d_smpl);
4057 dat_rddly0 = MSDC_Reg32(MSDC_DAT_RDDLY0);
4058 dat_rddly1 = MSDC_Reg32(MSDC_DAT_RDDLY1);
4059
4060 MSDC_NOTICE("[SD] <TUNE_RD_SS><%d> %s=%d, %s=%d, %s=%d, %s=%d\r\n",
4061 times_small_r, "CKMOD", clk_mode,
4062 "INT_DAT_L", int_dat_latch, "CKGEN_DLY", ckgen_dly,
4063 "R_D_SMPL", r_d_smpl);
4064 MSDC_NOTICE(" %s=0x%x, %s=0x%x\r\n",
4065 "DAT_RDDLY0", dat_rddly0, "DAT_RDDLY1", dat_rddly1);
4066
4067 if (ret)
4068 times_small_r = 0;
4069
4070 return ret;
4071
4072}
4073
4074SDC_CMD_STATUS SD_TuneRead(kal_uint32 data_adrs,void *rxbuffer,kal_uint32 num,kal_bool isLinkListBuf)
4075{
4076 kal_uint32 result = ERR_DAT_CRCERR;
4077
4078 do {
4079 /* Retry the Read with error handling */
4080 result = SD_ReqHandleData(data_adrs,rxbuffer,num,KAL_FALSE,isLinkListBuf);
4081
4082 if ((result == ERR_DAT_TIMEOUT) ||
4083 (result == NO_ERROR)) {
4084 if (result == NO_ERROR) {
4085 if (times_large_r)
4086 fgReadTuneLargeScale = 0;
4087
4088 times_small_r = 0;
4089 }
4090
4091 goto done;
4092 }
4093
4094 /* Large scale timing tuning */
4095 if (fgReadTuneLargeScale) {
4096 if (msdc_tune_read_large_scale())
4097 fgReadTuneLargeScale = 0;
4098 }
4099 /* Small scale timing tuning */
4100 else {
4101 if (msdc_tune_read_small_scale())
4102 goto done;
4103 }
4104
4105 } while (1);
4106
4107done:
4108 MSDC_CRIT("[SD] <TUNE_READ_DONE>");
4109 if (result == NO_ERROR)
4110 MSDC_CRIT(" %s\r\n", "PASS");
4111 else if (result == ERR_DAT_CRCERR)
4112 MSDC_CRIT(" %s\r\n", "CRCERR");
4113 else if (result == ERR_DAT_TIMEOUT)
4114 MSDC_CRIT(" %s\r\n", "TIMEOUT");
4115
4116 return result;
4117}
4118
4119void msdc_tune_init(void)
4120{
4121 /* Initialize the tuning releated parameters and registers */
4122 fgCMDTuneLargeScale = 1;
4123 times_large = 0;
4124 times_small = 0;
4125 MSDC_SET_FIELD_NPW(MSDC_PATCH_BIT1, MSDC_CMD_RSP_TA_CNTR, 0);
4126 MSDC_SET_FIELD_NPW(MSDC_IOCON, MSDC_IOCON_RSPL, 0);
4127 MSDC_SET_FIELD_NPW(MSDC_PAD_TUNE, MSDC_PAD_TUNE_CMDRDLY, 0);
4128
4129 fgWrTuneLargeScale = 1;
4130 times_large_w = 0;
4131 times_small_w = 0;
4132 MSDC_SET_FIELD_NPW(MSDC_PATCH_BIT1, MSDC_WRDAT_CRCS_TA_CNTR, 0);
4133 MSDC_SET_FIELD_NPW(MSDC_IOCON, MSDC_IOCON_WDSPL, 0);
4134 MSDC_SET_FIELD_NPW(MSDC_PAD_TUNE, MSDC_PAD_TUNE_DATWRDLY, 0);
4135
4136 fgReadTuneLargeScale = 1;
4137 times_large_r = 0;
4138 times_small_r = 0;
4139 MSDC_WriteReg32_NPW(MSDC_DAT_RDDLY0, 0);
4140 MSDC_WriteReg32_NPW(MSDC_DAT_RDDLY1, 0);
4141 MSDC_SET_FIELD_NPW(MSDC_PATCH_BIT0, MSDC_INT_DAT_LATCH_CK_SEL, 0);
4142 MSDC_SET_FIELD_NPW(MSDC_PATCH_BIT0, MSDC_CKGEN_MSDC_DLY_SEL, 0);
4143 MSDC_SET_FIELD_NPW(MSDC_IOCON, MSDC_IOCON_RDSPL, 0);
4144}
4145
4146SDC_CMD_STATUS SD_HandleWriteTMO(kal_uint32 address,void *txbuffer,kal_uint32 num,kal_bool isLinkListBuf)
4147{
4148 kal_uint32 cur_wrta,orig_wr_crcta;
4149 kal_uint32 status,i,ret;
4150
4151 ret=SD_GetStatus(gSD->mRCA,&status);
4152 if (ret){
4153 return ERR_DAT_TIMEOUT;
4154 }
4155 if (status&(R1_OUT_OF_RANGE_31|R1_ADDRESS_ERROR_30)){
4156 return ERR_DAT_TIMEOUT;
4157 }
4158 orig_wr_crcta=(MSDC_Reg32(MSDC_PATCH_BIT1)&MSDC_PATCH_BIT1_WRDAT_CRCS)>>(uffs(MSDC_PATCH_BIT1_WRDAT_CRCS)-1);
4159 /*Ncrc may cause Write data timeout*/
4160 for (i=0;i<8;i++){
4161 cur_wrta=(orig_wr_crcta+i)%8;
4162 MSDC_SetData32(MSDC_PATCH_BIT1,MSDC_PATCH_BIT1_WRDAT_CRCS,cur_wrta<<(uffs(MSDC_PATCH_BIT1_WRDAT_CRCS)-1));
4163 ret=SD_ReqHandleData(address,txbuffer,num,KAL_TRUE,isLinkListBuf);
4164 if (ret==0)
4165 return 0;
4166 if (ret==ERR_DAT_CRCERR||ret==ERR_CMD_RSPCRCERR)
4167 {
4168 return ret;
4169 }
4170 }
4171 if (ret)
4172 {
4173 return ret;
4174 }
4175 ret=SD_TuneWrite( address,txbuffer,num,isLinkListBuf);
4176 return ret;
4177}
4178/*************************************************************************
4179* FUNCTION
4180* SD_Reset
4181*
4182* DESCRIPTION
4183* reset all cards to idle state
4184*
4185* PARAMETERS
4186* 1. cmd: the content of SDC_CMD register
4187* 2. arg: the argument(if the command need no argument, fill it with 0)
4188*
4189* RETURNS
4190* SDC_CMD_STATUS
4191*
4192* GLOBALS AFFECTED
4193*
4194* NOTE
4195*
4196*************************************************************************/
4197SDC_CMD_STATUS SD_Reset(void)
4198{
4199 SDC_CMD_STATUS status;
4200 status=SD_SendCmd(SDC_CMD_CMD0,SDC_NO_ARG,MSDC_CMD_TIMEOUT);
4201 gSD->mState=IDLE_STA;
4202 return status;
4203
4204}
4205
4206/*************************************************************************
4207* FUNCTION
4208* SD_Cmd55
4209*
4210* DESCRIPTION
4211* APP_CMD: inidicate to the card that the next command is an application specified command
4212* rather than a standard command
4213*
4214* PARAMETERS
4215* rca: relative card address
4216*
4217* RETURNS
4218* SDC_CMD_STATUS
4219*
4220* GLOBALS AFFECTED
4221*
4222* NOTE
4223*
4224*************************************************************************/
4225SDC_CMD_STATUS SD_Cmd55(kal_uint16 rca)
4226{
4227 SDC_CMD_STATUS status;
4228
4229 if ((status = SD_SendCmd(SDC_CMD_CMD55, ((kal_uint32)rca << 16),MSDC_CMD_TIMEOUT)) != NO_ERROR)
4230 return status;
4231
4232 //read R1
4233 if ((status = SD_CheckStatus()) != NO_ERROR)
4234 return status;
4235
4236 //check APP_CMD bit in status register
4237 status=MSDC_Reg32(SDC_RESP0);
4238
4239 if (!(status & R1_APP_CMD_5))
4240 return ERR_APPCMD_FAILED;
4241
4242 return NO_ERROR;
4243
4244}
4245/*************************************************************************
4246* FUNCTION
4247* SD_Cmd8
4248*
4249* DESCRIPTION
4250* 1. Sends SD Memory Card interface conditions for support larger than 2G cards
4251* 2. check if the card is compliant to SD2.0 or higher
4252* 3. only performed while at IDLE state.
4253*
4254* PARAMETERS
4255*
4256* RETURNS
4257*
4258* GLOBALS AFFECTED
4259* gSD->mIsCMD8
4260*
4261*************************************************************************/
4262void SD_Cmd8(void)
4263{
4264 kal_uint32 resp;
4265 kal_uint32 retry = 4;
4266 MSDC_DEBUG("[SD][%s %d]Cmd8 arg=%x\r\n",__FUNCTION__,__LINE__,SDC_CMD8_ARG);
4267
4268cmd8_retry:
4269 if (SD_SendCmd(SDC_CMD_CMD8, SDC_CMD8_ARG,MSDC_CMD_TIMEOUT) != NO_ERROR)
4270 {
4271 MSDC_ERR("[SD][%s %d]SDC_Cmd8 fail\r\n",__FUNCTION__,__LINE__);
4272 SD_Reset();
4273 gSD->mCMD8Resp = SD_CMD8_RESP_NORESP;
4274 return;
4275 }
4276
4277 resp= MSDC_Reg32(SDC_RESP0);
4278 MSDC_DEBUG("[SD][%s %d]Cmd8 resp=%x\r\n",__FUNCTION__,__LINE__,resp);
4279
4280 if (resp == SDC_CMD8_ARG)
4281 gSD->mCMD8Resp = SD_CMD8_RESP_VALID;
4282 else {
4283 MSDC_ERR("[SD]CMD8 check pattern error, %X(%X)\r\n",SDC_CMD8_ARG,resp);
4284
4285 if (retry--)
4286 goto cmd8_retry;
4287
4288 gSD->mCMD8Resp = SD_CMD8_RESP_INVALID;
4289 }
4290
4291 return;
4292}
4293
4294/*************************************************************************
4295* FUNCTION
4296* SD_Cmd1_MMC
4297*
4298* DESCRIPTION
4299* asks all cards in idle state to send their OCR in the response on the CMD line
4300*
4301* PARAMETERS
4302*
4303* RETURNS
4304* SDC_CMD_STATUS
4305*
4306* GLOBALS AFFECTED
4307* gSD
4308*
4309* NOTE
4310* only works for MMC
4311*
4312*************************************************************************/
4313extern kal_bool FTL_isPollingMode();
4314
4315SDC_CMD_STATUS SD_Cmd1_MMC(void)
4316{
4317 SDC_CMD_STATUS status;
4318 kal_uint32 _ocr, ocr_i, t2;
4319
4320 #if defined(SD_MMC_HIGH_DENSITY_SUPPORT)
4321
4322 if (gSD->mCMD8Resp == SD_CMD8_RESP_INVALID)
4323 return ERR_CMD8_INVALID;
4324
4325 ocr_i = (SDC_OCR_DEFAULT | MMC_HIGH_DESITY_CHECK_BIT);
4326 #else
4327 ocr_i = SDC_OCR_DEFAULT;
4328 #endif
4329
4330 if (gMSDC_Handle->is_init_timeout == KAL_TRUE)
4331 return ERR_R3_OCR_BUSY;
4332
4333 t2 = drv_get_current_time();
4334
4335 do
4336 {
4337 /*send cmd1*/
4338 if ((status=SD_SendCmd(SDC_CMD_CMD1,ocr_i,MSDC_CMD_TIMEOUT)) != NO_ERROR)
4339 return status;
4340
4341 _ocr=MSDC_Reg32(SDC_RESP0);
4342 MSDC_NOTICE("[SD]OCR = %x\r\n", _ocr);
4343
4344 if ((_ocr & SDC_OCR_DEFAULT) == 0)
4345 return ERR_OCR_NOT_SUPPORT;
4346
4347 if (!gMSDC_Handle->mIsPresent)
4348 return MSDC_CARD_NOT_PRESENT;
4349
4350 if (!(_ocr & SDC_OCR_BUSY))
4351 {
4352 if (drv_get_duration_ms(t2) > MSDC_TIMEOUT_PERIOD_INI)
4353 {
4354 gMSDC_Handle->is_init_timeout = KAL_TRUE;
4355 break;
4356 }
4357
4358 msdc_sleep(2);
4359 }
4360 else {
4361 MSDC_CRIT("[SD]OCR = %x\r\n", _ocr);
4362 break;
4363 }
4364 }
4365 while (1);
4366
4367 if (gMSDC_Handle->is_init_timeout)
4368 return ERR_CMD_TIMEOUT;
4369
4370#if defined(SD_MMC_HIGH_DENSITY_SUPPORT)
4371
4372 if ((_ocr & MMC_HIGH_DESITY_CHECK_MSK) == MMC_HIGH_DESITY_CHECK_BIT)
4373 {
4374 gSD->flags |= SD_FLAG_HCS_SUPPORT;
4375 gMSDC_Handle->mMSDC_type = MMC42_CARD;
4376 gSD->mIsBlkAddr = 1;
4377 }
4378 else
4379#endif
4380 gMSDC_Handle->mMSDC_type = MMC_CARD;
4381
4382 gSD->mInactive = KAL_FALSE;
4383 gSD->mSDC_ocr = _ocr;
4384 gSD->mState = READY_STA;
4385
4386 return NO_ERROR;
4387}
4388SDC_CMD_STATUS SD_Cmd11(void)
4389{
4390 SDC_CMD_STATUS status;
4391
4392 if ((status = SD_SendCmd(SDC_CMD_CMD11, SDC_NO_ARG,MSDC_CMD_TIMEOUT)) != NO_ERROR)
4393 {
4394 return status;
4395 }
4396 //read R1
4397 if ((status = SD_CheckStatus()) != NO_ERROR)
4398 return status;
4399
4400 return NO_ERROR;
4401
4402}
4403kal_int32 SD_SwitchVolt18()
4404{
4405 kal_uint32 status,t2;
4406 status=SD_Cmd11();
4407 if (status !=NO_ERROR)
4408 return status;
4409 /*make sure SDC is not BUSY*/
4410 if (MSDC_TIMEOUT_WAIT((!SD_IS_SDC_BUSY())&&MSDC_Check_Card_Present(),MSDC_CMD_TIMEOUT))
4411 {
4412 MSDC_ERR("[SD][%s %d]wait SDC busy timeout\r\n",__FUNCTION__,__LINE__);
4413 return ERR_STATUS;
4414 }
4415 /*check data[3:0] and cmd is lower by card*/
4416 if(MSDC_Reg32(MSDC_PS)&((1<<24)|(0xf<<16)))
4417 return CHECK_DATA_CMD_LOW_FAIL;
4418 /*pull up disabled in CMD and DAT[3:0]*/
4419 MSDC_ConfigPin(MSDC_PIN_PULL_NONE);
4420 /*switch signal voltage to 1.8v*/
4421 gMSDC_Handle->signal_volt=1800;
4422 MSDC_SetSignalPower(1,gMSDC_Handle->signal_volt);
4423 /*wait 5ms*/
4424 msdc_sleep(2);
4425 /*PULL UP enable in CMD and DAT[3:0]*/
4426 MSDC_ConfigPin(MSDC_PIN_PULL_UP);
4427 msdc_sleep(1);
4428 /*start to detect volt change */
4429 MSDC_SetBits32(MSDC_CFG,MSDC_CFG_BV18SDT);
4430 msdc_sleep(20);
4431 t2=drv_get_current_time();
4432 do{
4433 if(((status=MSDC_Reg32(MSDC_CFG))& MSDC_CFG_BV18SDT)==0);
4434 {
4435 if (status&MSDC_CFG_BV18PSS)
4436 {
4437 //pass to switch volt to 1.8v
4438 return NO_ERROR;
4439 }
4440 else
4441 {
4442 //fail to switch volt to 1.8v
4443 MSDC_ERR("[SD][%s %d]1.8v fail ,MSDC_CFG %x\r\n",__FUNCTION__,__LINE__,status);
4444 break;
4445 }
4446 }
4447 if (drv_get_duration_ms(t2) > MSDC_TIMEOUT_PERIOD_INI)
4448 {
4449 //detect volt change timeout
4450 MSDC_ERR("[SD][%s %d]detect volt change timeout\r\n",__FUNCTION__,__LINE__);
4451 break;
4452 }
4453 }while(1);
4454
4455 //come to here ,mean timeout or switch 1.8v fail
4456
4457 return ERR_STATUS;
4458}
4459/*************************************************************************
4460* FUNCTION
4461* SD_Acmd41_SD
4462*
4463* DESCRIPTION
4464* asks all cards in idle state to send their OCR in the response on the CMD line
4465* OCR: Operation Condition Register
4466*
4467* PARAMETERS
4468*
4469* RETURNS
4470* SDC_CMD_STATUS
4471*
4472* GLOBALS AFFECTED
4473* gSD
4474*
4475* NOTE
4476* only works for SD
4477*
4478*************************************************************************/
4479SDC_CMD_STATUS SD_Acmd41_SD(void)
4480{
4481 SDC_CMD_STATUS status;
4482 kal_uint32 _ocr = 0, ocr_i = 0, t2;
4483
4484#if defined(SD_MMC_HIGH_DENSITY_SUPPORT)
4485
4486 if (gSD->mCMD8Resp == SD_CMD8_RESP_NORESP)
4487 ocr_i = SDC_OCR_DEFAULT;
4488 else if (gSD->mCMD8Resp == SD_CMD8_RESP_VALID) {
4489 #if defined(MSDC_CONFIG_SD30_SUPPORT)
4490 if (TEMP_SINGLE_LINE == gMSDC_Handle->trySingleLine)
4491 ocr_i = (SDC_OCR_DEFAULT | SD_ACMD41_HCS);
4492 else
4493 ocr_i = (SDC_OCR_DEFAULT | SD_ACMD41_HCS |SD_ACMD41_S18R | SD_ACMD41_XPC);
4494
4495 #else
4496 ocr_i = (SDC_OCR_DEFAULT | SD_ACMD41_HCS);
4497 #endif
4498 }
4499 else if (gSD->mCMD8Resp == SD_CMD8_RESP_INVALID)
4500 return ERR_CMD8_INVALID;
4501
4502#else
4503 ocr_i = SDC_OCR_DEFAULT;
4504#endif
4505 MSDC_CRIT("[SD][%s %d]Host OCR = %x\r\n",__FUNCTION__,__LINE__,ocr_i);
4506 retry:
4507 gMSDC_Handle->is_init_timeout = KAL_FALSE;
4508 t2 = drv_get_current_time();
4509
4510 do
4511 {
4512 /*send ACMD41*/
4513 status = SD_Cmd55(SDC_RCA_DEFAULT);
4514
4515 if (status != NO_ERROR)
4516 {
4517 return status;
4518 }
4519
4520 status=SD_SendCmd(SDC_CMD_ACMD41, ocr_i, MSDC_CMD_TIMEOUT);
4521 if (status != NO_ERROR)
4522 {
4523 return status;
4524 }
4525
4526 /*check response*/
4527 _ocr = MSDC_Reg32(SDC_RESP0);
4528 MSDC_NOTICE("[SD]ACMD41 resp = %x\r\n", _ocr);
4529
4530 if ((_ocr & SDC_OCR_DEFAULT) == 0)
4531 return ERR_OCR_NOT_SUPPORT;
4532
4533 if (!gMSDC_Handle->mIsPresent)
4534 return ERR_CARD_NOT_PRESENT;
4535
4536 if (!(_ocr & SDC_OCR_BUSY))
4537 {
4538 /*if return busy ,we check timeout or not*/
4539 if (drv_get_duration_ms(t2) > MSDC_TIMEOUT_PERIOD_INI)
4540 {
4541 gMSDC_Handle->is_init_timeout = KAL_TRUE;
4542 MSDC_ERR("[SD]ACMD41 Polling BUSY timeout!\r\n");
4543 break;
4544 }
4545
4546 msdc_sleep(5);
4547 }
4548 else
4549 {
4550 /*not busy */
4551 MSDC_CRIT("[SD]OCR = %x\r\n", _ocr);
4552 break;
4553 }
4554 }
4555 while (1);
4556
4557 if (gMSDC_Handle->is_init_timeout)
4558 return ERR_R3_OCR_BUSY;
4559
4560 gSD->mInactive = KAL_FALSE;
4561 gSD->mSDC_ocr = _ocr;
4562#if defined(SD_MMC_HIGH_DENSITY_SUPPORT)
4563 gSD->flags |= SD_FLAG_SD_TYPE_CARD;
4564
4565 if (_ocr & SD_ACMD41_HCS)
4566 {
4567 #if defined(MSDC_CONFIG_SD30_SUPPORT)
4568 if (_ocr & SD_ACMD41_S18R )
4569 {
4570 status=SD_SwitchVolt18();
4571 if (status != NO_ERROR)
4572 {
4573 return status; //need delete
4574 //fail to switch to 1.8v ,so set signal voltage back to 3.3.v
4575 gMSDC_Handle->signal_volt=3300;
4576 MSDC_SetSignalPower(1,gMSDC_Handle->signal_volt);
4577 power_cycle(1);
4578 SD_Reset();
4579 SD_Cmd8();
4580 ocr_i = (SDC_OCR_DEFAULT | SD_ACMD41_HCS);
4581 goto retry;
4582 }
4583
4584 gSD->flags|=SD_FLAG_UHS_SUPPORT;
4585 gMSDC_Handle->mMSDC_type=SD30_CARD;
4586 MSDC_CRIT("[SD][%s %d]SD3.0 UHS Card\r\n",__FUNCTION__,__LINE__);
4587 }
4588 else
4589 #endif
4590 {
4591 gSD->flags |= SD_FLAG_HCS_SUPPORT;
4592 gMSDC_Handle->mMSDC_type = SD20_HCS_CARD;
4593 MSDC_CRIT("[SD][%s %d]SD2.0 High Capacity Card\r\n",__FUNCTION__,__LINE__);
4594
4595 }
4596
4597
4598 }
4599 else if (gSD->mCMD8Resp == SD_CMD8_RESP_VALID)
4600 gMSDC_Handle->mMSDC_type = SD20_LCS_CARD;
4601 else
4602#endif
4603 gMSDC_Handle->mMSDC_type = SD_CARD;
4604
4605 gSD->mState = READY_STA;
4606
4607 return NO_ERROR;
4608
4609}
4610
4611/*************************************************************************
4612* FUNCTION
4613* SD_GetCID
4614*
4615* DESCRIPTION
4616* Read Card Identification.
4617*
4618* PARAMETERS
4619*
4620* RETURNS
4621* SDC_CMD_STATUS
4622*
4623* GLOBALS AFFECTED
4624* gSD
4625*
4626* NOTE
4627*
4628*
4629*************************************************************************/
4630
4631// Get CID(CMD2)
4632SDC_CMD_STATUS SD_GetCID(kal_uint32 *Cid)
4633{
4634 int i;
4635 SDC_CMD_STATUS status;
4636
4637 if ((status = SD_SendCmd(SDC_CMD_CMD2, SDC_NO_ARG,MSDC_CMD_TIMEOUT)) != NO_ERROR)
4638 {
4639 return status;
4640 }
4641
4642 //read R2
4643 for (i = 0; i < 4; i++)
4644 {
4645 Cid[i]=MSDC_Reg32((SDC_RESP0 + i * sizeof(kal_uint32)));
4646 }
4647
4648 SD_AnalysisCID(Cid);
4649 gSD->mState = IDENT_STA;
4650
4651 return NO_ERROR;
4652
4653}
4654
4655/*************************************************************************
4656* FUNCTION
4657* SD_ValidateRCA
4658*
4659* DESCRIPTION
4660* assing or read RCA
4661*
4662* PARAMETERS
4663* pRca: used for input or output RCA
4664*
4665* RETURNS
4666* SDC_CMD_STATUS
4667*
4668* GLOBALS AFFECTED
4669* gSD
4670*
4671* NOTE
4672* RCA is assinged to MMC card fixed to SDC_RCA_MMC(1)
4673*
4674*************************************************************************/
4675
4676// assign or read RCA
4677SDC_CMD_STATUS SD_ValidateRCA(kal_uint16* pRca)
4678{
4679 SDC_CMD_STATUS status;
4680 kal_uint32 resp;
4681 kal_uint8 state;
4682 kal_uint32 retry;
4683
4684#if defined(SD_MMC_HIGH_DENSITY_SUPPORT)
4685
4686 if (gSD->flags & SD_FLAG_SD_TYPE_CARD )
4687#else
4688 if (gMSDC_Handle->mMSDC_type == SD_CARD)
4689#endif
4690 {
4691 //read RCA form card
4692 retry=10;
4693 /*if card return RCA=0 we will retry,*/
4694 while(retry--)
4695 {
4696 MSDC_DEBUG("[SD][%s %d]send cmd3\r\n",__FUNCTION__,__LINE__);
4697 if ((status = SD_SendCmd(SDC_CMD_CMD3, SDC_NO_ARG,MSDC_CMD_TIMEOUT)) != NO_ERROR)
4698 return status;
4699
4700 //read R6
4701 resp=MSDC_Reg32(SDC_RESP0);
4702 MSDC_DEBUG("[SD][%s %d]cmd3 reps=%x\r\n",__FUNCTION__,__LINE__,resp);
4703#ifdef MSDC_TRACE_LEVEL1
4704 MD_TRC_MSDC_INFORM_R0(resp, __LINE__);
4705#endif
4706 if ((resp>>16)!=0)
4707 {
4708 *pRca = resp >> 16;
4709 gSD->mRCA = *pRca;
4710 break;
4711 }
4712 MSDC_DEBUG("[SD][%s %d]gSD->mRCA=%x\r\n",__FUNCTION__,__LINE__,gSD->mRCA);
4713 }
4714 if (retry==0)
4715 {
4716 /*always return RCA=0*/
4717 return ERR_RCA_FAIL;
4718 }
4719
4720 }
4721 else
4722 {
4723 //assign RCA to card
4724 if ((status = SD_SendCmd(SDC_CMD_CMD3_MMC, ((kal_uint32)SDC_RCA_MMC << 16),MSDC_CMD_TIMEOUT)) != NO_ERROR)
4725 return status;
4726
4727 //read R1
4728 resp=MSDC_Reg32(SDC_RESP0);
4729#ifdef MSDC_TRACE_LEVEL1
4730 MD_TRC_MSDC_INFORM_R0(resp, __LINE__);
4731#endif
4732 SD_GetStatus(SDC_RCA_MMC, &resp);
4733 state = 0;
4734 GetBitFieldN((kal_uint8*)&state, (kal_uint8*)&resp, 9, 4);
4735
4736 if (STBY_STA != state)
4737 return ERR_RCA_FAIL;
4738
4739 *pRca = gSD->mRCA = SDC_RCA_MMC;
4740 }
4741
4742 gSD->mState = STBY_STA;
4743 return NO_ERROR;
4744}
4745
4746/*************************************************************************
4747* FUNCTION
4748* SD_SetDSR
4749*
4750* DESCRIPTION
4751* set default value to the DSR
4752*
4753* PARAMETERS
4754*
4755* RETURNS
4756* SDC_CMD_STATUS
4757*
4758* GLOBALS AFFECTED
4759*
4760* NOTE
4761* SDC_DSR_DEFAULT(0x404)
4762*
4763*************************************************************************/
4764SDC_CMD_STATUS SD_SetDSR(void)
4765{
4766 return SD_SendCmd(SDC_CMD_CMD4, (kal_uint32)SDC_DSR_DEFAULT << 16,MSDC_CMD_TIMEOUT);
4767}
4768
4769/*************************************************************************
4770* FUNCTION
4771* SD_SelectCard
4772*
4773* DESCRIPTION
4774* select/deselect card
4775*
4776* PARAMETERS
4777* rca: relative card address
4778*
4779* RETURNS
4780* SDC_CMD_STATUS
4781*
4782* GLOBALS AFFECTED
4783*
4784* NOTE
4785*
4786*************************************************************************/
4787SDC_CMD_STATUS SD_SelectCard(kal_uint16 rca)
4788{
4789 SDC_CMD_STATUS status;
4790 MSDC_DEBUG("[SD][%s %d]send cmd7\r\n",__FUNCTION__,__LINE__);
4791
4792 if ((status = SD_SendCmd(SDC_CMD_CMD7, ((kal_uint32)rca << 16),MSDC_CMD_TIMEOUT)) != NO_ERROR)
4793 {
4794 return status;
4795 }
4796
4797 //read R1b
4798 if ((status = SD_WaitCardNotBusy(MSDC_DATA_TIMEOUT)) != NO_ERROR)
4799 return status;
4800
4801 if ((status = SD_CheckStatus()) != NO_ERROR)
4802 return status;
4803
4804 return NO_ERROR;
4805}
4806
4807/*************************************************************************
4808* FUNCTION
4809* SD_GetCSD
4810*
4811* DESCRIPTION
4812* Get CSD from addressed card
4813*
4814* PARAMETERS
4815* rca: relative card address
4816* Csd: used for containing read CSD
4817*
4818* RETURNS
4819* SDC_CMD_STATUS
4820*
4821* GLOBALS AFFECTED
4822*
4823* NOTE
4824*
4825*************************************************************************/
4826SDC_CMD_STATUS SD_GetCSD(kal_uint16 rca, kal_uint32 Csd[4])
4827{
4828 SDC_CMD_STATUS status;
4829 kal_uint32 i;
4830 MSDC_DEBUG("[SD][%s %d]send cmd9\r\n",__FUNCTION__,__LINE__);
4831
4832 if ((status = SD_SendCmd(SDC_CMD_CMD9, ((kal_uint32)rca << 16),MSDC_CMD_TIMEOUT)) != NO_ERROR)
4833 {
4834 return status;
4835 }
4836
4837
4838 // read R2
4839 for (i = 0; i < 4; i++)
4840 {
4841 Csd[i]=MSDC_Reg32((volatile kal_uint32 *)(SDC_RESP0 + i * 4));
4842 #ifdef MSDC_DEBUG_PRINT
4843 MSDC_DEBUG("%x ",Csd[i]);
4844 #endif
4845 }
4846 #ifdef MSDC_DEBUG_PRINT
4847 MSDC_DEBUG("\r\n ");
4848 #endif
4849 // analysis CSD...
4850 SD_AnalysisCSD(Csd);
4851
4852 return NO_ERROR;
4853}
4854
4855// addressed send CID
4856SDC_CMD_STATUS SD_GetAddressedCID(kal_uint16 rca, kal_uint32 Cid[4])
4857{
4858 SDC_CMD_STATUS status;
4859 kal_uint32 i;
4860
4861 if ((status = SD_SendCmd(SDC_CMD_CMD10, (kal_uint32)rca << 16,MSDC_CMD_TIMEOUT)) != NO_ERROR)
4862 return status;
4863
4864 // read R2
4865 for (i = 0; i < 4; i++)
4866 {
4867#ifndef DRV_LSD
4868 Cid[i]=MSDC_Reg32((volatile kal_uint32 *)(SDC_RESP0 + i * 4));
4869#else
4870 Cid[i]=MSDC_Reg32(SDC_RESP0 + i);
4871#endif
4872 }
4873
4874 return NO_ERROR;
4875}
4876
4877
4878/*************************************************************************
4879* FUNCTION
4880* SD_StopTrans
4881*
4882* DESCRIPTION
4883* Stop Muli-Block operation
4884*
4885* PARAMETERS
4886*
4887* RETURNS
4888* SDC_CMD_STATUS
4889*
4890* GLOBALS AFFECTED
4891*
4892* NOTE
4893* definition of SD_STOP_SLOW is used for some erroneous card
4894*************************************************************************/
4895SDC_CMD_STATUS SD_StopTrans(void)
4896{
4897 SDC_CMD_STATUS status;
4898 #define CMD12_TIMEOUT_MS 1000
4899 status = SD_SendCmd(SDC_CMD_CMD12,SDC_NO_ARG,MSDC_CMD_TIMEOUT);
4900 MSDC_CLR_FIFO();
4901 return status;
4902
4903}
4904
4905/*************************************************************************
4906* FUNCTION
4907* SD_GetStatus
4908*
4909* DESCRIPTION
4910* addressed send status
4911*
4912* PARAMETERS
4913*
4914* RETURNS
4915* SDC_CMD_STATUS
4916*
4917* GLOBALS AFFECTED
4918*
4919* NOTE
4920*
4921*************************************************************************/
4922SDC_CMD_STATUS SD_GetStatus(kal_uint16 rca, kal_uint32* resp)
4923{
4924 SDC_CMD_STATUS status;
4925
4926 if ((status = SD_SendCmd(SDC_CMD_CMD13, ((kal_uint32)rca << 16),MSDC_CMD_TIMEOUT)) != NO_ERROR)
4927 return status;
4928
4929 *resp=MSDC_Reg32(SDC_RESP0);
4930
4931 return NO_ERROR;
4932}
4933
4934/*************************************************************************
4935* FUNCTION
4936* SD_SetBlength
4937*
4938* DESCRIPTION
4939* set block length
4940*
4941* PARAMETERS
4942* BKLength: block length u want to set
4943*
4944* RETURNS
4945* SDC_CMD_STATUS
4946*
4947* GLOBALS AFFECTED
4948* gSD->mBKLength
4949*
4950* NOTE
4951*
4952*************************************************************************/
4953SDC_CMD_STATUS SD_SetBlength(kal_uint32 BKLength)
4954{
4955 SDC_CMD_STATUS status;
4956
4957 // maximal value of block length is 2048
4958 if (BKLength > SDC_MAX_BKLENGTH)
4959 return ERR_INVALID_BKLENGTH;
4960
4961 if (!gSD->mCSD.r_blk_part && BKLength < gSD->mCSD.max_r_blk_len )
4962 return ERR_INVALID_BKLENGTH;
4963 if ((status = SD_SendCmd(SDC_CMD_CMD16, BKLength,MSDC_CMD_TIMEOUT)) != NO_ERROR)
4964 return status;
4965
4966 //read R1
4967 status = SD_CheckStatus();
4968 // 2. configure the controller
4969 gSD->mBKLength = BKLength;
4970 // BitFieldWrite32((kal_uint32*)SDC_CMD, BKLength, SDC_CMD_BLKLEN);
4971 return status;
4972}
4973
4974
4975/*************************************************************************
4976* FUNCTION
4977* SD_ReadSingleBlock
4978*
4979* DESCRIPTION
4980* 1. read a single block form data_adrs of card to the rxbuffer
4981* 2. the block length is set by set block length
4982*
4983* PARAMETERS
4984* data_adrs: starting address to read
4985* rxbuffer: as name
4986*
4987* RETURNS
4988* SDC_CMD_STATUS
4989*
4990* GLOBALS AFFECTED
4991*
4992* NOTE
4993* the size of rxbuffer should be 4*n (n : integer)
4994*
4995*************************************************************************/
4996#ifdef DRV_MSDC_SLIM
4997SDC_CMD_STATUS SD_ReadSingleBlock(kal_uint32 data_adrs, kal_uint32* rxbuffer) // slim
4998{
4999 return SD_ReadMultiBlock(data_adrs, rxbuffer, 1); // slim
5000}
5001#else
5002SDC_CMD_STATUS SD_ReadSingleBlock(kal_uint32 data_adrs, kal_uint32* rxbuffer)
5003{
5004 return SD_ReadMultiBlock(data_adrs, rxbuffer, 1);
5005}
5006#endif
5007/*************************************************************************
5008* FUNCTION
5009* SD_ReadMultiBlock
5010*
5011* DESCRIPTION
5012* read num of blocks into rxbuffer
5013*
5014* PARAMETERS
5015* data_adrs: starting address to read
5016* rxbuffer: as name
5017* num: number of blocks to read
5018*
5019* RETURNS
5020* SDC_CMD_STATUS
5021*
5022* GLOBALS AFFECTED
5023*
5024* NOTE
5025*
5026*************************************************************************/
5027#ifdef DRV_MSDC_SLIM
5028SDC_CMD_STATUS
5029SD_ReadMultiBlock(kal_uint32 data_adrs, kal_uint32* rxbuffer, kal_uint32 num_blk) // slim
5030{
5031
5032
5033}
5034#else
5035SDC_CMD_STATUS SD_ReadMultiBlock(kal_uint32 data_adrs, kal_uint32* rxbuffer, kal_uint32 num_blk)
5036{
5037 kal_uint32 status;
5038
5039 status = SD_ReqHandleData(data_adrs, rxbuffer,num_blk, KAL_FALSE,KAL_FALSE);
5040 if (status==ERR_DAT_CRCERR)
5041 {
5042 status=SD_TuneRead(data_adrs,rxbuffer,num_blk,KAL_FALSE);
5043 }
5044 return status;
5045}
5046#endif
5047
5048
5049
5050/*************************************************************************
5051* FUNCTION
5052* SD_WriteSingleBlock
5053*
5054* DESCRIPTION
5055* write a single block
5056*
5057* PARAMETERS
5058* address: starting address to write
5059* txbuffer: as name
5060*
5061* RETURNS
5062* SDC_CMD_STATUS
5063*
5064* GLOBALS AFFECTED
5065*
5066* NOTE
5067* block length is set by Set_Block_Length
5068*
5069*************************************************************************/
5070#ifdef DRV_MSDC_SLIM
5071//__attribute__ ((section ("EXT_BOOTLOADER_CODE"))) SDC_CMD_STATUS SD_WriteSingleBlock(kal_uint32 address, kal_uint32* txbuffer) // slim
5072SDC_CMD_STATUS SD_WriteSingleBlock(kal_uint32 address, kal_uint32* txbuffer)
5073{
5074 return SD_WriteMultiBlock(address, txbuffer, 1); // slim
5075}
5076#else
5077//__attribute__ ((section ("EXT_BOOTLOADER_CODE"))) SDC_CMD_STATUS SD_WriteSingleBlock(kal_uint32 address, kal_uint32* txbuffer)
5078SDC_CMD_STATUS SD_WriteSingleBlock(kal_uint32 address, kal_uint32* txbuffer)
5079{
5080 return SD_WriteMultiBlock(address, txbuffer, 1);
5081}
5082#endif
5083
5084void SD_Sleep4Wait(kal_int32 sleep_tick)
5085{
5086
5087}
5088/*************************************************************************
5089* FUNCTION
5090* SD_WriteMultiBlock
5091*
5092* DESCRIPTION
5093* write num blocks starting at address
5094*
5095* PARAMETERS
5096* address: starting address to write
5097* txbuffer: as name
5098* num: number of blocks to write
5099*
5100* RETURNS
5101* SDC_CMD_STATUS
5102*
5103* GLOBALS AFFECTED
5104*
5105* NOTE
5106* block length is set by Set_Block_Length
5107*
5108*************************************************************************/
5109//#ifndef DRV_MSDC_SLIM
5110//__attribute__ ((section ("EXT_BOOTLOADER_CODE"))) SDC_CMD_STATUS SD_WriteMultiBlock(kal_uint32 address, kal_uint32* txbuffer, kal_uint32 num)
5111SDC_CMD_STATUS SD_WriteMultiBlock(kal_uint32 address, kal_uint32* txbuffer, kal_uint32 num_blk)
5112{
5113 SDC_CMD_STATUS status;
5114
5115 if (gSD->mWPEnabled)
5116 return ERR_WRITE_PROTECT;
5117 if ((status=SD_ReqHandleData(address, txbuffer, num_blk, KAL_TRUE,KAL_FALSE))!=NO_ERROR)
5118 {
5119 if (status ==ERR_DAT_CRCERR)
5120 {
5121 status=SD_TuneWrite(address,txbuffer,num_blk,KAL_FALSE);
5122 }
5123 else if (status == ERR_DAT_TIMEOUT)
5124 {
5125 status=SD_HandleWriteTMO(address,txbuffer,num_blk,KAL_FALSE);
5126 }
5127 }
5128
5129 return status;
5130}
5131
5132SDC_CMD_STATUS SD_GpdWriteMultiBlock(kal_uint32 address ,kal_uint32 num_blk,void *gpd_data)
5133{
5134 SDC_CMD_STATUS status;
5135
5136 gMSDC_Handle->f_tuning = 0;
5137
5138 if (gSD->mWPEnabled)
5139 return ERR_WRITE_PROTECT;
5140 if ((status=SD_ReqHandleData(address, gpd_data, num_blk, KAL_TRUE,KAL_TRUE))!=NO_ERROR)
5141 {
5142 gMSDC_Handle->f_tuning = 1;
5143
5144 if (status ==ERR_DAT_CRCERR)
5145 {
5146 status=SD_TuneWrite(address,gpd_data,num_blk,KAL_TRUE);
5147 }
5148 else if (status == ERR_DAT_TIMEOUT)
5149 {
5150 status=SD_HandleWriteTMO(address,gpd_data,num_blk,KAL_TRUE);
5151 }
5152 }
5153 return status;
5154}
5155
5156SDC_CMD_STATUS SD_GpdReadMultiBlock(kal_uint32 address ,kal_uint32 num_blk,void *gpd_data )
5157{
5158 kal_uint32 status;
5159
5160 gMSDC_Handle->f_tuning = 0;
5161 status = SD_ReqHandleData(address, gpd_data,num_blk, KAL_FALSE,KAL_TRUE);
5162
5163 if (status==ERR_DAT_CRCERR)
5164 {
5165 gMSDC_Handle->f_tuning = 1;
5166 status=SD_TuneRead(address,gpd_data,num_blk,KAL_TRUE);
5167 }
5168 return status;
5169}
5170
5171
5172//#else
5173//__attribute__ ((section ("EXT_BOOTLOADER_CODE"))) SDC_CMD_STATUS SD_WriteMultiBlock(kal_uint32 address, kal_uint32* txbuffer, kal_uint32 num) // slim
5174//SDC_CMD_STATUS SD_WriteMultiBlock(kal_uint32 address, kal_uint32* txbuffer, kal_uint32 num) // slim
5175//{
5176
5177
5178//}
5179//#endif
5180
5181
5182/*************************************************************************
5183* FUNCTION
5184* SD_SetBusWidth
5185*
5186* DESCRIPTION
5187* ACMD6: set the data width 00 for 1 bit, 10 for 4 bits
5188*
5189* PARAMETERS
5190* width: indicate the bus width
5191*
5192* RETURNS
5193* SDC_CMD_STATUS
5194*
5195* GLOBALS AFFECTED
5196*
5197* NOTE
5198* Not every card support 4-bits bus
5199* only for SD
5200*
5201*************************************************************************/
5202SDC_CMD_STATUS SD_SetBusWidth(SD_BITWIDTH width)
5203{
5204 SDC_CMD_STATUS status;
5205 MSDC_DEBUG("[SD][%s %d]send ACMD6 ,change bus width to %d\r\n",__FUNCTION__,__LINE__,width);
5206
5207 // check if card support 4 bits bus
5208 if ((width == BIT_4W) && !(gSD->mSCR.bus_width & 0x04))
5209 return ERR_NOT_SUPPORT_4BITS;
5210
5211 // send APP_CMD
5212 if ((status = SD_Cmd55(gSD->mRCA)) != NO_ERROR)
5213 return status;
5214
5215 // send cmd6
5216 if ((status = SD_SendCmd(SDC_CMD_ACMD6, width,MSDC_CMD_TIMEOUT)) != NO_ERROR)
5217 return status;
5218
5219 //read R1
5220 if ((status = SD_CheckStatus()) != NO_ERROR)
5221 return status;
5222
5223
5224 // set the controler bus width
5225 MSDC_SetBusWidth(width);
5226 gSD->bus_width = width;
5227 return NO_ERROR;
5228}
5229
5230/*************************************************************************
5231* FUNCTION
5232* SD_ReadSCR
5233*
5234* DESCRIPTION
5235* ACMD51: read the SD Configuration Register(8bytes block read)
5236*
5237* PARAMETERS
5238* scr: used for store SCR
5239*
5240* RETURNS
5241* SDC_CMD_STATUS
5242*
5243* GLOBALS AFFECTED
5244*
5245* NOTE
5246* Make sure the size of SCR is 8 bytes
5247*
5248*************************************************************************/
5249SDC_CMD_STATUS SD_ReadSCR(kal_uint32* scr)
5250{
5251 SDC_CMD_STATUS status;
5252 kal_uint32 blklen;
5253
5254 ASSERT((kal_uint32)scr % 4 == 0);
5255
5256 MSDC_DEBUG("[SD][%s %d]send cmd55\r\n",__FUNCTION__,__LINE__);
5257
5258 // send APP_CMD
5259 if ((status = SD_Cmd55(gSD->mRCA)) != NO_ERROR)
5260 return status;
5261
5262 // set block number
5263 blklen=gSD->mBKLength;
5264 gSD->mBKLength = 8;
5265 MSDC_WriteReg32(SDC_BLK_NUM,1);
5266 MSDC_DEBUG("[SD][%s %d]send acmd51\r\n",__FUNCTION__,__LINE__);
5267
5268 // set to pio mode and clear fifo
5269 BitFieldWrite32((kal_uint32 *)MSDC_CFG, 1, MSDC_CFG_PIO);
5270 gMSDC_Handle->dma_xfer=0;
5271 MSDC_CLR_FIFO();
5272
5273 // send command
5274 if ((status = SD_SendCmd(SDC_CMD_ACMD51, SDC_NO_ARG,MSDC_CMD_TIMEOUT)) != NO_ERROR)
5275 return status;
5276
5277 // read R1
5278 if ((status = SD_CheckStatus()) != NO_ERROR)
5279 return status;
5280
5281 // read data(8bytes)
5282 status=SD_WaitDatRdyOrTo(scr,8,KAL_FALSE);
5283 if (status !=NO_ERROR)
5284 return status;
5285 MSDC_DEBUG("[SD][%s %d]scr=%x %x\r\n",__FUNCTION__,__LINE__,*scr,*(scr+1));
5286
5287 SD_AnalysisSCR(scr);
5288 MSDC_CLR_FIFO();
5289
5290 gSD->mBKLength = blklen;
5291
5292 return NO_ERROR;
5293
5294}
5295
5296static kal_uint32 unstuff_sd_status(kal_uint32 *raw_sd_status, kal_uint32 start, kal_uint32 size)
5297{
5298 kal_uint32 __mask = (1 << (size)) - 1;
5299 int __off = 63 - ((start) / 8);
5300 int __shft;
5301 kal_uint8 *raw = (kal_uint8 *)raw_sd_status;
5302 kal_uint32 __res = 0;
5303
5304 if ((start & 7) + 1 >= size)
5305 {
5306 __shft = ((start & 7) + 1) - size;
5307 __res = raw[__off] >> __shft;
5308 }
5309 else if (size <= 32)
5310 {
5311 size -= ((start & 7) + 1);
5312 __shft = size;
5313 __res = raw[__off] << __shft;
5314 while (size)
5315 {
5316 __off++;
5317 if (size >= 8)
5318 {
5319 size -= 8;
5320 __res |= raw[__off] << size;
5321 }
5322 else
5323 {
5324 __mask = (1 << (size)) - 1;
5325 __res |= (raw[__off] >> (8 - size)) & __mask;
5326 size = 0;
5327 }
5328 }
5329 }
5330 return __res & __mask;
5331}
5332#define UNSTUFF_SD_STATUS(r,s,sz) unstuff_sd_status(r,s,sz)
5333
5334/*************************************************************************
5335* FUNCTION
5336* SD_ReadSDStatus
5337*
5338* DESCRIPTION
5339* ACMD13: read the SD Status Register(64bytes block read)
5340*
5341* PARAMETERS
5342* sd_status: used for store SD Status
5343*
5344* RETURNS
5345* SDC_CMD_STATUS
5346*
5347* GLOBALS AFFECTED
5348*
5349* NOTE
5350* Make sure the size of SD Status is 64 bytes
5351*
5352*************************************************************************/
5353SDC_CMD_STATUS SD_ReadSDStatus(kal_uint32* sd_status)
5354{
5355 SDC_CMD_STATUS status;
5356 kal_uint32 blklen;
5357
5358 ASSERT((kal_uint32)sd_status % 4 == 0);
5359
5360 MSDC_DEBUG("[SD][%s %d]send cmd55\r\n",__FUNCTION__,__LINE__);
5361
5362 // send APP_CMD
5363 if ((status = SD_Cmd55(gSD->mRCA)) != NO_ERROR)
5364 return status;
5365
5366 // set block number
5367 blklen=gSD->mBKLength;
5368 gSD->mBKLength = 64;
5369 MSDC_WriteReg32(SDC_BLK_NUM,1);
5370 MSDC_DEBUG("[SD][%s %d]send acmd13\r\n",__FUNCTION__,__LINE__);
5371
5372 // set to pio mode and clear fifo
5373 BitFieldWrite32((kal_uint32 *)MSDC_CFG, 1, MSDC_CFG_PIO);
5374 gMSDC_Handle->dma_xfer=0;
5375
5376 // send command
5377 if ((status = SD_SendCmd(SDC_CMD_ACMD13, SDC_NO_ARG,MSDC_CMD_TIMEOUT)) != NO_ERROR)
5378 return status;
5379
5380 // read R1
5381 if ((status = SD_CheckStatus()) != NO_ERROR)
5382 return status;
5383
5384 // read data(8bytes)
5385 status=SD_WaitDatRdyOrTo(sd_status,64,KAL_FALSE);
5386 gSD->mBKLength = blklen;
5387
5388 if (status !=NO_ERROR)
5389 return status;
5390 MSDC_DEBUG("[SD][%s %d]sd_status=%x %x\r\n",__FUNCTION__,__LINE__,*sd_status,*(sd_status+1));
5391
5392 gSD->mSDSts.dat_bus_width = UNSTUFF_SD_STATUS(sd_status, 511, 2);
5393 gSD->mSDSts.secured_mode = UNSTUFF_SD_STATUS(sd_status, 509, 1);
5394 gSD->mSDSts.sd_card_type = UNSTUFF_SD_STATUS(sd_status, 495, 16);
5395 gSD->mSDSts.size_of_prot_area = UNSTUFF_SD_STATUS(sd_status, 479, 32);
5396 gSD->mSDSts.speed_class = UNSTUFF_SD_STATUS(sd_status, 447, 8);
5397 gSD->mSDSts.perf_move = UNSTUFF_SD_STATUS(sd_status, 439, 8);
5398 gSD->mSDSts.au_size = UNSTUFF_SD_STATUS(sd_status, 431, 4);
5399 gSD->mSDSts.erase_size = UNSTUFF_SD_STATUS(sd_status, 423, 16);
5400 gSD->mSDSts.erase_timeout = UNSTUFF_SD_STATUS(sd_status, 407, 6);
5401 gSD->mSDSts.erase_offset = UNSTUFF_SD_STATUS(sd_status, 401, 2);
5402 gSD->mSDSts.uhs_speed_grade = UNSTUFF_SD_STATUS(sd_status, 399, 4);
5403 gSD->mSDSts.uhs_au_size = UNSTUFF_SD_STATUS(sd_status, 395, 4);
5404
5405 /* If it is a SD ROM Card, set the WP flag */
5406 if (gSD->mSDSts.sd_card_type == 0x0001) {
5407 gSD->mWPEnabled = KAL_TRUE;
5408 MSDC_CRIT("[SD]It is a ROM Card!\r\n");
5409 }
5410
5411 return NO_ERROR;
5412
5413}
5414
5415
5416/*************************************************************************
5417* FUNCTION
5418* SD_SetPreEraseBlk
5419*
5420* DESCRIPTION
5421* ACMD23: set the number of write blocksto be pre-erased before writing
5422* used for faster multiple Block Write
5423*
5424* PARAMETERS
5425* num: used for storing number of blocks during multi-block operation
5426*
5427* RETURNS
5428* SDC_CMD_STATUS
5429*
5430* GLOBALS AFFECTED
5431*
5432* NOTE
5433*
5434*************************************************************************/
5435SDC_CMD_STATUS SD_SetPreEraseBlk(kal_uint32 num)
5436{
5437 SDC_CMD_STATUS status;
5438
5439 //[22:0] number of blocks
5440 num &= 0x003FFF;
5441
5442 // send APP_CMD
5443 if ((status = SD_Cmd55(gSD->mRCA)) != NO_ERROR)
5444 return status;
5445
5446 // send CMD23
5447 if ((status = SD_SendCmd(SDC_CMD_ACMD23, num,MSDC_CMD_TIMEOUT)) != NO_ERROR)
5448 return status;
5449
5450 //read R1
5451 if ((status = SD_CheckStatus()) != NO_ERROR)
5452 return status;
5453
5454 return NO_ERROR;
5455
5456}
5457
5458/*************************************************************************
5459* FUNCTION
5460* SD_EraseCmdClass
5461*
5462* DESCRIPTION
5463* groups of erase commands including CMD32 ~CMD38
5464*
5465* PARAMETERS
5466* cmd: indicate which command to execute
5467* address: starting address wiht write protection
5468*
5469* RETURNS
5470* SDC_CMD_STATUS
5471*
5472* GLOBALS AFFECTED
5473*
5474* NOTE
5475* CMD34~CMD37 are only for MMC
5476*
5477*************************************************************************/
5478SDC_CMD_STATUS SD_EraseCmdClass(kal_uint32 cmd , kal_uint32 address)
5479{
5480 SDC_CMD_STATUS status;
5481 kal_uint32 sdcard_status;
5482 kal_set_eg_events(gMSDC_Handle->MSDC_Events, 0, KAL_AND);
5483
5484 if (cmd != SDC_CMD_CMD38)
5485 {
5486 if ((status = SD_SendCmd(cmd, address,MSDC_CMD_TIMEOUT)) != NO_ERROR)
5487 return status;
5488 }
5489 else if ((status = SD_SendCmd(cmd, SDC_NO_ARG,MSDC_CMD_TIMEOUT)) != NO_ERROR)
5490 return status;
5491
5492 //read R1
5493 if ((status = SD_CheckStatus()) != NO_ERROR)
5494 return status;
5495
5496
5497 if (cmd == SDC_CMD_CMD38)
5498 {
5499
5500 if ((status = SD_WaitCardNotBusy(MSDC_DATA_TIMEOUT)) != NO_ERROR)
5501 return status;
5502
5503 do
5504 {
5505 if ((status = SD_GetStatus(gSD->mRCA, (kal_uint32*)&sdcard_status)) != NO_ERROR)
5506 return status;
5507
5508 if (gMSDC_Handle->mIsPresent == KAL_FALSE)
5509 return ERR_INVALID_CARD;
5510 }
5511 while (R1_CURRENT_STATE(sdcard_status) != TRAN_STA);
5512 }
5513
5514 return NO_ERROR;
5515}
5516/*************************************************************************
5517* FUNCTION
5518* SD_Switch_MMC40
5519*
5520* DESCRIPTION
5521* CMD6: set the command set or write to the EXT_CSD (for MMC4.0)
5522*
5523* PARAMETERS
5524* access: access mode
5525* index: index to EXT_CSD
5526* value: value to write to EXT_CSD
5527* set: selected command set
5528*
5529* RETURNS
5530* SDC_CMD_STATUS
5531*
5532* GLOBALS AFFECTED
5533*
5534* NOTE
5535*
5536*************************************************************************/
5537SDC_CMD_STATUS SD_Switch_MMC40(kal_uint8 access, kal_uint8 index, kal_uint8 value, kal_uint8 set)
5538{
5539 SDC_CMD_STATUS status = NO_ERROR;
5540 kal_uint32 arg = 0;
5541 kal_uint32 resp = 0;
5542 kal_bool retry = KAL_FALSE;
5543// kal_uint8 *pData = NULL;
5544
5545switch_start:
5546
5547 arg = (access << 24) | (index << 16) | (value << 8) | set;
5548
5549 // send command
5550 if ((status = SD_SendCmd(SDC_CMD_CMD6_MMC, arg,MSDC_CMD_TIMEOUT)) != NO_ERROR)
5551 {
5552 goto ERR_Exit;
5553 }
5554
5555#ifndef DRV_LSD
5556
5557 //read R1b
5558 if ((status = SD_WaitCardNotBusy(MSDC_DATA_TIMEOUT)) != NO_ERROR)
5559 goto ERR_Exit;
5560
5561#endif
5562
5563 SD_GetStatus(gSD->mRCA, (kal_uint32*)&status);
5564
5565 //read R1
5566 if ((status = SD_CheckStatus()) != NO_ERROR)
5567 goto ERR_Exit;
5568
5569 resp=MSDC_Reg32(SDC_RESP0);
5570
5571 if ((resp & MMC_SWITCH_ERROR) != 0)
5572 {
5573 if (retry == KAL_FALSE)
5574 {
5575#ifdef MSDC_TRACE_LEVEL2
5576 MD_TRC_MSDC_INFORM_R0(resp, __LINE__);
5577#endif
5578 retry = KAL_TRUE;
5579 goto switch_start;
5580 }
5581 else
5582 return ERR_MMC_SWITCH_ERROR;
5583 }
5584
5585 return NO_ERROR;
5586
5587ERR_Exit:
5588 return status;
5589}
5590
5591/*************************************************************************
5592* FUNCTION
5593* SD_SendEXTCSD_MMC40
5594*
5595* DESCRIPTION
5596* CMD8: read the content of EXT_CSD register
5597*
5598* PARAMETERS
5599* kal: access mode
5600* index: index to EXT_CSD
5601* value: value to write to EXT_CSD
5602* set: selected command set
5603*
5604* RETURNS
5605* SDC_CMD_STATUS
5606*
5607* GLOBALS AFFECTED
5608*
5609* NOTE
5610*
5611*************************************************************************/
5612#if 0
5613/* under construction !*/
5614/* under construction !*/
5615/* under construction !*/
5616/* under construction !*/
5617/* under construction !*/
5618/* under construction !*/
5619/* under construction !*/
5620/* under construction !*/
5621/* under construction !*/
5622#ifdef DRV_LSD
5623/* under construction !*/
5624#endif
5625/* under construction !*/
5626/* under construction !*/
5627/* under construction !*/
5628/* under construction !*/
5629/* under construction !*/
5630/* under construction !*/
5631/* under construction !*/
5632/* under construction !*/
5633/* under construction !*/
5634/* under construction !*/
5635/* under construction !*/
5636/* under construction !*/
5637/* under construction !*/
5638/* under construction !*/
5639/* under construction !*/
5640/* under construction !*/
5641/* under construction !*/
5642/* under construction !*/
5643/* under construction !*/
5644/* under construction !*/
5645/* under construction !*/
5646/* under construction !*/
5647/* under construction !*/
5648/* under construction !*/
5649/* under construction !*/
5650/* under construction !*/
5651/* under construction !*/
5652/* under construction !*/
5653/* under construction !*/
5654/* under construction !*/
5655/* under construction !*/
5656/* under construction !*/
5657/* under construction !*/
5658/* under construction !*/
5659/* under construction !*/
5660/* under construction !*/
5661#else
5662SDC_CMD_STATUS SD_SendEXTCSD_MMC40(kal_uint32* rxbuffer)
5663{
5664 SDC_CMD_STATUS status;
5665 kal_uint32 blklen;
5666 // SDC_CMD_STATUS status1;
5667 // kal_bool retry = KAL_FALSE;
5668 //kal_uint32 idx = 0;
5669
5670 //start:
5671 blklen=gSD->mBKLength;
5672 gSD->mBKLength = 512;
5673 MSDC_WriteReg32(SDC_BLK_NUM,1);
5674 //set to pio mode and clear fifo
5675 BitFieldWrite32((kal_uint32 *)MSDC_CFG, 1, MSDC_CFG_PIO);
5676 gMSDC_Handle->dma_xfer=0;
5677 MSDC_CLR_FIFO();
5678
5679 // read the block of 512 bytes (make sure the rxbuffer is 4 byte aligned)
5680 if ((status = SD_SendCmd(SDC_CMD_CMD8_MMC40, SDC_NO_ARG,MSDC_CMD_TIMEOUT)) != NO_ERROR)
5681 goto ERR_Exit;
5682
5683 //read R1
5684 if ((status = SD_CheckStatus()) != NO_ERROR)
5685 goto ERR_Exit;
5686
5687 //idx = 0;
5688 /*move data from FIFO to buffer*/
5689 if ((status = SD_WaitDatRdyOrTo(rxbuffer,512,KAL_FALSE))!=NO_ERROR)
5690 {
5691 goto ERR_Exit;
5692 }
5693
5694 kal_mem_cpy(MSDC_eCSD, rxbuffer, 512);
5695 gSD->mCSD.ext_csd = (T_EXT_CSD_MMC40 *)MSDC_eCSD;//rxbuffer;
5696 gSD->mBKLength=blklen;
5697 return NO_ERROR;
5698
5699ERR_Exit:
5700
5701 MSDC_FatalErrorHandle();
5702 return status;
5703}
5704#endif
5705/*************************************************************************
5706* FUNCTION
5707* SD_CheckTimeoutWithSleep
5708*
5709* DESCRIPTION
5710* check timeout or not and sleep 1 tick if has been waited more than 10 ms
5711*
5712* PARAMETERS
5713* start_time: the time start to wait, get with drv_get_current_time
5714* duration_ms: the timeout limitation
5715*
5716* RETURNS
5717* kal_bool, timeout:KAL_TRUE; not timeout:KAL_FALSE;
5718*
5719* GLOBALS AFFECTED
5720* gMSDC_Handle->is_timeout
5721*
5722* NOTE:
5723* This function should be called in the wait loop to prevent block other tasks.
5724*
5725*************************************************************************/
5726kal_bool SD_CheckTimeoutWithSleep(kal_int32 start_time,
5727 kal_int32 duration_ms)
5728{
5729 kal_int32 elapsed_time = drv_get_duration_ms(start_time);
5730 //check timeout or not
5731 if(elapsed_time > duration_ms)
5732 {
5733 gMSDC_Handle->is_timeout = KAL_TRUE;
5734 return KAL_TRUE;
5735 }
5736 gMSDC_Handle->is_timeout = KAL_FALSE;
5737
5738 if(elapsed_time < 10)
5739 {
5740 return KAL_FALSE;
5741 }
5742 else if ((KAL_FALSE == kal_query_systemInit())
5743#ifdef __TST_WRITE_TO_FILE__/*error recording: considering error recording additionally*/
5744 && (KAL_FALSE == INT_QueryExceptionStatus())
5745#endif
5746 && (KAL_FALSE == kal_if_hisr())
5747 && (KAL_FALSE == kal_if_lisr()))
5748 {
5749 kal_sleep_task(1);
5750 }
5751 return KAL_FALSE;
5752
5753}
5754
5755/*************************************************************************
5756* FUNCTION
5757* SD_Switch_SD11
5758*
5759* DESCRIPTION
5760* CMD6: switch command to query and select the specific functions. (SD1.1 or later)
5761* PARAMETERS
5762* arg: argument
5763* resp: buffer to contain the ther 64 bytes status information
5764*
5765* RETURNS
5766* SDC_CMD_STATUS
5767*
5768* GLOBALS AFFECTED
5769*
5770* NOTE
5771*
5772*************************************************************************/
5773SDC_CMD_STATUS SD_Switch_SD11(kal_uint32 arg, T_SWITCH_STATUS* info)
5774{
5775 SDC_CMD_STATUS status = NO_ERROR;
5776 kal_uint32 blklen;
5777 gSD->mBKNum=1;
5778 blklen=gSD->mBKLength;
5779 gSD->mBKLength = SD_CMD6_RESP_LEN;
5780 MSDC_WriteReg32(SDC_BLK_NUM,1);
5781 //set to pio mode and clear fifo
5782 BitFieldWrite32((kal_uint32 *)MSDC_CFG, 1, MSDC_CFG_PIO);
5783 gMSDC_Handle->dma_xfer=0;
5784 MSDC_CLR_FIFO();
5785
5786 if ((status = SD_SendCmd(SDC_CMD_CMD6_SD11, arg,MSDC_CMD_TIMEOUT)) != NO_ERROR)
5787 return status;
5788
5789 if ((status = SD_CheckStatus()) != NO_ERROR)
5790 return status;
5791
5792 status=SD_WaitDatRdyOrTo((kal_uint32 *)info,SD_CMD6_RESP_LEN,KAL_FALSE);
5793 gSD->mBKLength=blklen;
5794 return status;
5795}
5796
5797/*************************************************************************
5798* FUNCTION
5799* SD_Switch_SD11
5800*
5801* DESCRIPTION
5802* Enable the high speed interface to support up to 50M Hz clock
5803*
5804* PARAMETERS
5805* arg: argument
5806* resp: buffer to contain the ther 64 bytes status information
5807*
5808* RETURNS
5809* SDC_CMD_STATUS
5810*
5811* GLOBALS AFFECTED
5812*
5813* NOTE
5814*
5815*************************************************************************/
5816
5817#ifndef DRV_MSDC_CORRECT_CMD6
5818SDC_CMD_STATUS SD_SelectHighSpeed_SD11(void)
5819{
5820 SDC_CMD_STATUS status;
5821 T_SWITCH_STATUS *p = (T_SWITCH_STATUS*)MSDC_Sector;
5822 MSDC_DEBUG("[SD][%s %d]send cmd6 \r\n",__FUNCTION__,__LINE__);
5823
5824 if ((status = SD_Switch_SD11(SD_CMD6_QUERY_HIGH_SPEED, p)) != NO_ERROR)
5825 return status;
5826
5827 if (p->max_current == 0)
5828 return ERR_SD_HS_FAIL;
5829
5830 if ((p->group1_info & (1 << SD_FUNC_HIGH_SPEED)) &&
5831 (p->group1_result == SD_FUNC_HIGH_SPEED))
5832 {
5833 if ((status = SD_Switch_SD11(SD_CMD6_SELECT_HIGH_SPEED, p)) != NO_ERROR)
5834 return status;
5835
5836 if (p->max_current == 0)
5837 return ERR_SD_HS_FAIL;
5838
5839 if (p->group1_result == SD_FUNC_HIGH_SPEED)
5840 gSD->flags |= SD_FLAG_HS_SUPPORT;
5841 }
5842 else
5843 return ERR_SD_HS_FAIL;
5844
5845
5846 return NO_ERROR;
5847}
5848#else
5849typedef struct
5850{
5851 kal_uint16 max_current;
5852 kal_uint16 group1_info;
5853 kal_uint16 group1_status;
5854 kal_uint8 group1_result;
5855 kal_uint8 structure_version;
5856}T_Group1SwitchStatus;
5857/*************************************************************************
5858* FUNCTION
5859* SD_ParseGroup1FunctionStatus
5860*
5861* DESCRIPTION
5862* Parse the Group1 functons' information form the data returned by CMD6
5863*
5864* PARAMETERS
5865* arg:
5866* T_Group1SwitchStatus* sf_status : information of group1 function
5867* kal_uint8* crude_info : crude data returned by CMD6
5868* resp:
5869*
5870* RETURNS
5871* void
5872*
5873* GLOBALS AFFECTED
5874* None
5875* NOTE
5876*
5877*************************************************************************/
5878void SD_ParseGroup1FunctionStatus(T_Group1SwitchStatus* sf_status, kal_uint8* crude_info)
5879{
5880 sf_status->max_current = (((*(kal_uint8 *)crude_info) << 8)
5881 | (*(kal_uint8 *)(crude_info + 1)));
5882 sf_status->group1_info = (((*(kal_uint8 *)(crude_info + 12)) << 8)
5883 | (*(kal_uint8 *)(crude_info + 13)));
5884 sf_status->group1_result = ((*(kal_uint8 *)(crude_info + 16)) & 0xf);
5885 sf_status->structure_version = (*(kal_uint8 *)(crude_info + 17));
5886 sf_status->group1_status = (((*(kal_uint8 *)(crude_info + 28)) << 8)
5887 | (*(kal_uint8 *)(crude_info + 29)));
5888}
5889/*************************************************************************
5890* FUNCTION
5891* SD_QuerySwithHighSpeed
5892*
5893* DESCRIPTION
5894* Send CMD6 with query or swith and check the response data.
5895*
5896* PARAMETERS
5897* arg: kal_uint32 arg
5898* resp:
5899*
5900* RETURNS
5901* SDC_CMD_STATUS
5902*
5903* GLOBALS AFFECTED
5904* MSDC_Sector
5905* NOTE
5906*
5907*************************************************************************/
5908SDC_CMD_STATUS SD_QuerySwithHighSpeed(kal_uint32 arg)
5909{
5910 T_Group1SwitchStatus sf_status;
5911 SDC_CMD_STATUS cmd_status;
5912 if ((cmd_status = SD_Switch_SD11(arg, (T_SWITCH_STATUS*)MSDC_Sector)) != NO_ERROR)
5913 return cmd_status;
5914 SD_ParseGroup1FunctionStatus(&sf_status,(kal_uint8*)MSDC_Sector);
5915 if (0 == sf_status.max_current)
5916 return ERR_HIGH_SPEED_CONSUMPTION;
5917 if ((SD_FUNC_HIGH_SPEED == sf_status.group1_result)\
5918 && (0==(sf_status.group1_status & (1 << SD_FUNC_HIGH_SPEED))))
5919 return NO_ERROR;//the high speed function can be switched
5920 if ((0xF == sf_status.group1_result) || (!(sf_status.group1_info & (1 << SD_FUNC_HIGH_SPEED))))
5921 return ERR_HIGH_SPEED_NOT_SUPPORT;//not support
5922 if (sf_status.group1_status & (1 << SD_FUNC_HIGH_SPEED))//busy
5923 return ERR_HIGH_SPEED_BUSY;
5924 return ERR_HIGH_SPEED_COMMON_ERROR;
5925}
5926/*************************************************************************
5927* FUNCTION
5928* SD_SelectHighSpeed_SD11
5929*
5930* DESCRIPTION
5931* Select high speed mode for the SD card that supports CMD6
5932*
5933* PARAMETERS
5934* arg: void
5935* resp:
5936*
5937* RETURNS
5938* SDC_CMD_STATUS
5939*
5940* GLOBALS AFFECTED
5941* gSD->flags
5942* NOTE
5943*
5944*************************************************************************/
5945
5946SDC_CMD_STATUS SD_SelectHighSpeed_SD11(void)
5947{
5948 SDC_CMD_STATUS high_speed_status;
5949 kal_int32 t1;
5950 t1 = drv_get_current_time();
5951 do
5952 {
5953 high_speed_status = SD_QuerySwithHighSpeed(SD_CMD6_QUERY_HIGH_SPEED);//query
5954 dbg_print("query high_speed_status: %x\r\n",high_speed_status);
5955 if (NO_ERROR == high_speed_status)
5956 {
5957 high_speed_status = SD_QuerySwithHighSpeed(SD_CMD6_SELECT_HIGH_SPEED);//switch
5958 dbg_print("switch high_speed_status: %x\r\n",high_speed_status);
5959 if (NO_ERROR == high_speed_status)
5960 {
5961 gSD->flags |= SD_FLAG_HS_SUPPORT;
5962 return NO_ERROR;
5963 }
5964 if (ERR_HIGH_SPEED_BUSY != high_speed_status)
5965 break;
5966 }
5967 if (ERR_HIGH_SPEED_BUSY != high_speed_status)
5968 break;
5969 if (drv_get_duration_ms(t1)>500)
5970 return ERR_HIGH_SPEED_TIMEOUT;
5971 //if(SD_CheckTimeoutWithSleep(t1,500))
5972 // return ERR_HIGH_SPEED_TIMEOUT;//timeout
5973 }while(1);
5974 return high_speed_status;
5975}
5976
5977#endif
5978
5979void parse_Cmd6FunctionStatus(T_SWITCH_STATUS *new_status,kal_uint8 * cur_Status)
5980{
5981 new_status->max_current=((*(kal_uint8*)cur_Status)<<8)\
5982 | (*(kal_uint8 *)(cur_Status+1));
5983 new_status->ver=(*(kal_uint8 *)(cur_Status+17));
5984 new_status->group1_info=((*(kal_uint8 *)(cur_Status+12))<<8)\
5985 | (*(kal_uint8 *)(cur_Status+13));
5986 new_status->group1_result=(*(kal_uint8*)(cur_Status+16))&0xf;
5987 new_status->group1_busy=((*(kal_uint8*)(cur_Status+28))<<8)\
5988 | (*(kal_uint8 *)(cur_Status+29));
5989
5990 new_status->group2_info=((*(kal_uint8 *)(cur_Status+10))<<8)\
5991 | (*(kal_uint8 *)(cur_Status+11));
5992 new_status->group2_result=((*(kal_uint8*)(cur_Status+16))>>4)&0xf;
5993 new_status->group2_busy=((*(kal_uint8*)(cur_Status+26))<<8)\
5994 | (*(kal_uint8 *)(cur_Status+27));
5995
5996 new_status->group3_info=((*(kal_uint8 *)(cur_Status+8))<<8)\
5997 | (*(kal_uint8 *)(cur_Status+9));
5998 new_status->group3_result=(*(kal_uint8*)(cur_Status+15))&0xf;
5999 new_status->group3_busy=((*(kal_uint8*)(cur_Status+24))<<8)\
6000 | (*(kal_uint8 *)(cur_Status+25));
6001
6002 new_status->group4_info=((*(kal_uint8 *)(cur_Status+6))<<8)\
6003 | (*(kal_uint8 *)(cur_Status+7));
6004 new_status->group4_result=((*(kal_uint8*)(cur_Status+15))>>4)&0xf;
6005 new_status->group4_busy=((*(kal_uint8*)(cur_Status+22))<<8)\
6006 | (*(kal_uint8 *)(cur_Status+23));
6007
6008 new_status->group5_info=((*(kal_uint8 *)(cur_Status+4))<<8)\
6009 | (*(kal_uint8 *)(cur_Status+5));
6010 new_status->group5_result=(*(kal_uint8*)(cur_Status+14))&0xf;
6011 new_status->group5_busy=((*(kal_uint8*)(cur_Status+20))<<8)\
6012 | (*(kal_uint8 *)(cur_Status+21));
6013
6014 new_status->group6_info=((*(kal_uint8 *)(cur_Status+2))<<8)\
6015 | (*(kal_uint8 *)(cur_Status+3));
6016 new_status->group6_result=((*(kal_uint8*)(cur_Status+14))>>4)&0xf;
6017 new_status->group6_busy=((*(kal_uint8*)(cur_Status+18))<<8)\
6018 | (*(kal_uint8 *)(cur_Status+19));
6019 /*
6020 dbg_print("new_status->group1_info :%x\r\n",new_status->group1_info);
6021 dbg_print("new_status->group1_result:%x\r\n",new_status->group1_result);
6022 dbg_print("new_status->group1_busy:%x\r\n",new_status->group1_busy);
6023
6024 dbg_print("new_status->group2_info :%x\r\n",new_status->group2_info);
6025 dbg_print("new_status->group2_result:%x\r\n",new_status->group2_result);
6026 dbg_print("new_status->group2_busy:%x\r\n",new_status->group2_busy);
6027
6028 dbg_print("new_status->group3_info :%x\r\n",new_status->group3_info);
6029 dbg_print("new_status->group3_result:%x\r\n",new_status->group3_result);
6030 dbg_print("new_status->group3_busy:%x\r\n",new_status->group3_busy);
6031
6032 dbg_print("new_status->group4_info :%x\r\n",new_status->group4_info);
6033 dbg_print("new_status->group4_result:%x\r\n",new_status->group4_result);
6034 dbg_print("new_status->group4_busy:%x\r\n",new_status->group4_busy);
6035
6036 dbg_print("new_status->group5_info :%x\r\n",new_status->group5_info);
6037 dbg_print("new_status->group5_result:%x\r\n",new_status->group5_result);
6038 dbg_print("new_status->group5_busy:%x\r\n",new_status->group5_busy);
6039
6040 dbg_print("new_status->group6_info :%x\r\n",new_status->group6_info);
6041 dbg_print("new_status->group6_result:%x\r\n",new_status->group6_result);
6042 dbg_print("new_status->group6_busy:%x\r\n",new_status->group6_busy);
6043 dbg_print("new_status->max_current:%x\r\n",new_status->max_current);
6044 dbg_print("new_status->ver:%x\r\n",new_status->ver);
6045 */
6046
6047}
6048
6049SDC_CMD_STATUS SD_CheckSwitch(void)
6050{
6051 //read the function support by current card
6052 kal_uint32 status;
6053 T_SWITCH_STATUS funcStatus;
6054
6055 char *uhs_mode[] = {"SDR12", "SDR25", "SDR50", "SDR104", "DDR50"};
6056 char *speed_mode[] = {"DS", "HS"};
6057 char *drv_strength[] = {"TYPE_A", "TYPE_B", "TYPE_C", "TYPE_D"};
6058 char *cur_limit[] = {"200mA", "400mA", "600mA", "800mA"};
6059
6060 if ((status = SD_Switch_SD11(SD_CMD6_QUERY_SUPPORT_FUNCTION, (T_SWITCH_STATUS*)MSDC_Sector)) != NO_ERROR)
6061 return status;
6062 parse_Cmd6FunctionStatus(&funcStatus,(kal_uint8*)MSDC_Sector);
6063 gSD->card_support.function1=funcStatus.group1_info;
6064 gSD->card_support.function2=funcStatus.group2_info;
6065 gSD->card_support.function3=funcStatus.group3_info;
6066 gSD->card_support.function4=funcStatus.group4_info;
6067 #if defined(MSDC_CONFIG_SD30_SUPPORT)
6068 if (gMSDC_Handle->mMSDC_type==SD30_CARD)
6069 {
6070 //for SD3.0
6071 /*set bus speed mode*/
6072 if(gSD->card_support.function1&gMSDC_Handle->host_support.function1&FUN1_SDR104)
6073 gSD->function_set.function1=FUN1_SET_SDR104;
6074 else if(gSD->card_support.function1&gMSDC_Handle->host_support.function1&FUN1_DDR50)
6075 gSD->function_set.function1=FUN1_SET_DDR50;
6076 else if(gSD->card_support.function1&gMSDC_Handle->host_support.function1&FUN1_SDR50)
6077 gSD->function_set.function1=FUN1_SET_SDR50;
6078 else if(gSD->card_support.function1&gMSDC_Handle->host_support.function1&FUN1_SDR25_HS)
6079 gSD->function_set.function1=FUN1_SET_SDR25_HS;
6080 else
6081 gSD->function_set.function1=FUN1_SET_SDR12_DS;
6082 /*set command system*/
6083 gSD->function_set.function2=FUN2_SET_DEFAULT;
6084 /*set driver strength */
6085 if (gSD->card_support.function3&gMSDC_Handle->host_support.function3&FUN3_TYPE_A)
6086 gSD->function_set.function3=FUN3_SET_TYPE_A;
6087 else if(gSD->card_support.function3&gMSDC_Handle->host_support.function3&FUN3_TYPE_B)
6088 gSD->function_set.function3=FUN3_SET_TYPE_B;
6089 else if(gSD->card_support.function3&gMSDC_Handle->host_support.function3&FUN3_TYPE_C)
6090 gSD->function_set.function3=FUN3_SET_TYPE_C;
6091 else if(gSD->card_support.function3&gMSDC_Handle->host_support.function3&FUN3_TYPE_D)
6092 gSD->function_set.function3=FUN3_SET_TYPE_D;
6093 else
6094 gSD->function_set.function3=FUN3_SET_TYPE_A;
6095 /*set current limit*/
6096 if (gSD->function_set.function1==FUN1_SET_SDR104||gSD->function_set.function1==FUN1_SET_DDR50
6097 ||gSD->function_set.function1==FUN1_SET_SDR50)
6098 {
6099 if(gSD->card_support.function4&gMSDC_Handle->host_support.function4&FUN4_800MA)
6100 gSD->function_set.function4=FUN4_SET_800MA;
6101 else if (gSD->card_support.function4&gMSDC_Handle->host_support.function4&FUN4_600MA)
6102 gSD->function_set.function4=FUN4_SET_600MA;
6103 else if (gSD->card_support.function4&gMSDC_Handle->host_support.function4&FUN4_400MA)
6104 gSD->function_set.function4=FUN4_SET_400MA;
6105 else
6106 gSD->function_set.function4=FUN4_SET_200MA;
6107 }
6108 else
6109 {
6110 gSD->function_set.function4=FUN4_SET_200MA;
6111 }
6112
6113 MSDC_CRIT("[SD][%s]Switch to %s speed mode! \r\n", __FUNCTION__,
6114 uhs_mode[gSD->function_set.function1]);
6115 MSDC_CRIT("[SD][%s]Switch to %s drive strength! \r\n", __FUNCTION__,
6116 drv_strength[gSD->function_set.function3]);
6117 MSDC_CRIT("[SD][%s]Switch to %s current limit! \r\n", __FUNCTION__,
6118 cur_limit[gSD->function_set.function4]);
6119 }
6120 else
6121 #endif
6122 {
6123 //for 2.0 HS DS card
6124 if(gSD->card_support.function1&gMSDC_Handle->host_support.function1&FUN1_SDR25_HS)
6125 gSD->function_set.function1=FUN1_SET_SDR25_HS;
6126 else
6127 gSD->function_set.function1=FUN1_SET_SDR12_DS;
6128
6129 MSDC_CRIT("[SD][%s]Switch to %s speed mode! \r\n", __FUNCTION__,
6130 speed_mode[gSD->function_set.function1]);
6131 }
6132 return NO_ERROR;
6133
6134}
6135
6136SDC_CMD_STATUS SD_QuerySwith(kal_uint32 cmd6_arg)
6137{
6138
6139 SDC_CMD_STATUS cmd_status;
6140 T_SWITCH_STATUS card_support;
6141 if ((cmd_status = SD_Switch_SD11(cmd6_arg, (T_SWITCH_STATUS*)MSDC_Sector)) != NO_ERROR)
6142 return cmd_status;
6143 parse_Cmd6FunctionStatus(&card_support,(kal_uint8*)MSDC_Sector);
6144 /*
6145 dbg_print("card_support.group1_info :%x\r\n",card_support.group1_info);
6146 dbg_print("card_support.group1_result:%x\r\n",card_support.group1_result);
6147 dbg_print("card_support.group1_busy:%x\r\n",card_support.group1_busy);
6148
6149 dbg_print("card_support.group2_info :%x\r\n",card_support.group2_info);
6150 dbg_print("card_support.group2_result:%x\r\n",card_support.group2_result);
6151 dbg_print("card_support.group2_busy:%x\r\n",card_support.group2_busy);
6152
6153 dbg_print("card_support.group3_info :%x\r\n",card_support.group3_info);
6154 dbg_print("card_support.group3_result:%x\r\n",card_support.group3_result);
6155 dbg_print("card_support.group3_busy:%x\r\n",card_support.group3_busy);
6156
6157 dbg_print("card_support.group4_info :%x\r\n",card_support.group4_info);
6158 dbg_print("card_support.group4_result:%x\r\n",card_support.group4_result);
6159 dbg_print("card_support.group4_busy:%x\r\n",card_support.group4_busy);
6160
6161 dbg_print("card_support.group5_info :%x\r\n",card_support.group5_info);
6162 dbg_print("card_support.group5_result:%x\r\n",card_support.group5_result);
6163 dbg_print("card_support.group5_busy:%x\r\n",card_support.group5_busy);
6164
6165 dbg_print("card_support.group6_info :%x\r\n",card_support.group6_info);
6166 dbg_print("card_support.group6_result:%x\r\n",card_support.group6_result);
6167 dbg_print("card_support.group6_busy:%x\r\n",card_support.group6_busy);
6168 dbg_print("card_support.max_current:%x\r\n",card_support.max_current);
6169 dbg_print("card_support.ver:%x\r\n",card_support.ver);
6170 */
6171 if (0 == card_support.max_current)
6172 return ERR_HIGH_SPEED_CONSUMPTION;
6173 #if defined(MSDC_CONFIG_SD30_SUPPORT)
6174 if (gMSDC_Handle->mMSDC_type==SD30_CARD)
6175 {
6176 if ((gSD->function_set.function1==card_support.group1_result)\
6177 &&(0==(card_support.group1_busy &(1<<(gSD->function_set.function1)))))
6178 {
6179
6180 if ((gSD->function_set.function3==card_support.group3_result)\
6181 &&(0==(card_support.group3_busy &(1<<(gSD->function_set.function3)))))
6182 {
6183
6184 if ((gSD->function_set.function4==card_support.group4_result)\
6185 &&(0==(card_support.group4_busy &(1<<(gSD->function_set.function4)))))
6186 {
6187
6188 return NO_ERROR;
6189 }
6190 }
6191 }
6192 dbg_print("gSD->function_set.function1=%x card_support.group1_result=%x\r\n",gSD->function_set.function1,card_support.group1_result);
6193 dbg_print("gSD->function_set.function3=%x card_support.group3_result=%x\r\n",gSD->function_set.function3,card_support.group3_result);
6194 dbg_print("gSD->function_set.function4=%x card_support.group4_result=%x\r\n",gSD->function_set.function4,card_support.group4_result);
6195 dbg_print("busy1 %x busy3 %x busy4 %x\r\n",(card_support.group1_busy &(1<<(gSD->function_set.function1)))\
6196 ,(card_support.group3_busy &(1<<(gSD->function_set.function3)))\
6197 ,(card_support.group4_busy &(1<<(gSD->function_set.function4))));
6198 if ((0xF == card_support.group1_result)\
6199 || (!(card_support.group1_info & (1<<(gSD->function_set.function1)))))
6200 return ERR_SPEED_MODE_UNSUPPORT;//not support
6201 if ((0xF == card_support.group3_result)\
6202 || (!(card_support.group3_info & (1<<(gSD->function_set.function3)))))
6203 return ERR_DRIVER_TYPE_UNSUPPORT;//not support
6204 if ((0xF == card_support.group4_result)\
6205 || (!(card_support.group4_info & (1<<(gSD->function_set.function4)))))
6206 return ERR_CURRENT_LIMIT_UNSUPPORT;//not support
6207
6208
6209 if (card_support.group1_busy & (1 << (gSD->function_set.function1)))//busy
6210 return ERR_SWITCH_BUSY;
6211 if (card_support.group3_busy & (1 << (gSD->function_set.function3)))//busy
6212 return ERR_SWITCH_BUSY;
6213 if (card_support.group4_busy & (1 << (gSD->function_set.function4)))//busy
6214 return ERR_SWITCH_BUSY;
6215 }
6216 else
6217 #endif
6218 {
6219 if ((gSD->function_set.function1==card_support.group1_result)\
6220 &&(0==(card_support.group1_busy &(1<<(gSD->function_set.function1)))))
6221 return NO_ERROR;
6222 if ((0xF == card_support.group1_result)\
6223 || (!(card_support.group1_info & (1<<(gSD->function_set.function1)))))
6224 return ERR_HIGH_SPEED_NOT_SUPPORT;//not support
6225 if (card_support.group1_busy & (1 << (gSD->function_set.function1)))//busy
6226 return ERR_HIGH_SPEED_BUSY;
6227 }
6228
6229 return ERR_HIGH_SPEED_COMMON_ERROR;
6230}
6231
6232SDC_CMD_STATUS SD_SwitchSpeedMode(void)
6233{
6234 kal_uint32 status,set_function;
6235 kal_int32 t1;
6236
6237 if (gSD->mSCR.spec_ver<SCR_SEC_VER_1)
6238 {
6239 gSD->function_set.function1=0;
6240 return NO_ERROR;
6241 }
6242 if (!(gSD->mCSD.ccc&CCC_SWITCH))
6243 {
6244 gSD->function_set.function1=0;
6245 return NO_ERROR;
6246 }
6247
6248 t1 = drv_get_current_time();
6249 if ((status =SD_CheckSwitch()) != NO_ERROR)
6250 return status;
6251 #if defined(MSDC_CONFIG_SD30_SUPPORT)
6252 if (gMSDC_Handle->mMSDC_type==SD30_CARD)
6253 {
6254 set_function=0x00ff0000|gSD->function_set.function1|(gSD->function_set.function3<<8)|(gSD->function_set.function4<<12);
6255 }
6256 else
6257 #endif
6258 {
6259 set_function=0x00fffff0|gSD->function_set.function1;
6260 }
6261 do
6262 {
6263 status = SD_QuerySwith(SD_CMD6_QUERY_SWITCH|set_function);//query
6264 if (NO_ERROR == status)
6265 {
6266 status = SD_QuerySwith(SD_CMD6_SELECT_SWITCH|set_function);//switch
6267 if (NO_ERROR == status)
6268 {
6269 if (gMSDC_Handle->mMSDC_type==SD30_CARD)
6270 {
6271 gSD->flags |= SD_FLAG_UHS_ENABLED;
6272 }
6273 else if (gSD->function_set.function1==1)
6274 {
6275 gSD->flags |= SD_FLAG_HS_ENABLED;
6276 }
6277
6278 return NO_ERROR;
6279 }
6280 if (ERR_SWITCH_BUSY != status)
6281 break;
6282 }
6283 if (ERR_SWITCH_BUSY != status)
6284 break;
6285 if (drv_get_duration_ms(t1)>500)
6286 return ERR_SWITCH_TIMEOUT;
6287 }while(1);
6288 return status;
6289}
6290SDC_CMD_STATUS SD_GoInactive(kal_uint16 rca)
6291{
6292 SDC_CMD_STATUS status;
6293
6294 if ((status = SD_SendCmd(SDC_CMD_CMD15, (kal_uint32)rca << 16,MSDC_CMD_TIMEOUT)) != NO_ERROR)
6295 return status;
6296
6297 return NO_ERROR;
6298}
6299
6300SDC_CMD_STATUS SD_ReadStream_MMC(kal_uint32 address, kal_uint32* rxbuffer, kal_uint32 bytes)
6301{
6302
6303 return 0;
6304}
6305
6306
6307// write data stream from card only for MMC
6308SDC_CMD_STATUS SD_WriteStream_MMC(kal_uint32 address, kal_uint32* txbuffer, kal_uint32 bytes)
6309{
6310 return 0;
6311}
6312
6313//program CSD, transfer CSD through data line
6314SDC_CMD_STATUS SD_ProgramCSD(kal_uint32 Csd[4])
6315{
6316 SDC_CMD_STATUS status;
6317 kal_uint32 blklen;
6318 //set block length to 16 , num to 1
6319
6320 gSD->mBKNum=1;
6321 blklen=gSD->mBKLength;
6322 gSD->mBKLength = 16;
6323 MSDC_WriteReg32(SDC_BLK_NUM,1);
6324 //set to pio mode and clear fifo
6325 BitFieldWrite32((kal_uint32 *)MSDC_CFG, 1, MSDC_CFG_PIO);
6326 gMSDC_Handle->dma_xfer=0;
6327 MSDC_CLR_FIFO();
6328
6329
6330 if ((status = SD_SendCmd(SDC_CMD_CMD27, 0,MSDC_CMD_TIMEOUT)) != NO_ERROR)
6331 return status;
6332
6333 //read R1
6334 if ((status = SD_CheckStatus()) != NO_ERROR)
6335 {
6336 //SD_WaitDatRdyOrTo();
6337 return status;
6338 }
6339 //send CSD 128 bits
6340 status=SD_WaitDatRdyOrTo(Csd,16,KAL_TRUE);
6341 //set block length back to 512
6342 BitFieldWrite32((kal_uint32*)SDC_CMD, 512, SDC_CMD_BLKLEN);
6343 gSD->mBKLength=blklen;
6344 return status;
6345}
6346
6347
6348//set write protect
6349SDC_CMD_STATUS SD_SetWriteProtect(kal_uint32 address)
6350{
6351 SDC_CMD_STATUS status;
6352
6353 if ((status = SD_SendCmd(SDC_CMD_CMD28, address,MSDC_CMD_TIMEOUT)) != NO_ERROR)
6354 return status;
6355
6356 if ((status = SD_CheckStatus()) != NO_ERROR)
6357 return status;
6358
6359 //wait until data line is ready
6360 status =SD_WaitCardNotBusy(MSDC_DATA_TIMEOUT);
6361 return status;
6362}
6363
6364//clear write protect
6365SDC_CMD_STATUS SD_ClrWriteProtect(kal_uint32 address)
6366{
6367 SDC_CMD_STATUS status;
6368
6369 if ((status = SD_SendCmd(SDC_CMD_CMD29, address,MSDC_CMD_TIMEOUT)) != NO_ERROR)
6370 return status;
6371
6372 if ((status = SD_CheckStatus()) != NO_ERROR)
6373 return status;
6374
6375 status=SD_WaitCardNotBusy(MSDC_DATA_TIMEOUT);
6376 return status;
6377}
6378
6379// send write protect(single block read)
6380SDC_CMD_STATUS SD_SendWriteProtect(kal_uint32 address, kal_uint32* WPBits32)
6381{
6382 SDC_CMD_STATUS status;
6383 kal_uint32 tmp,blklen;
6384
6385
6386 BitFieldWrite32((kal_uint32*)SDC_CMD, 4, SDC_CMD_BLKLEN);
6387 blklen=gSD->mBKLength;
6388 gSD->mBKLength=4;
6389 MSDC_WriteReg32(SDC_BLK_NUM,1);
6390 MSDC_CLR_FIFO();
6391
6392 if ((status = SD_SendCmd(SDC_CMD_CMD30, address,MSDC_CMD_TIMEOUT)) != NO_ERROR)
6393 return status;
6394
6395 if ((status = SD_CheckStatus()) != NO_ERROR)
6396 return status;
6397
6398 //read 32 write protection bits
6399 tmp=MSDC_FIFO_READ32();
6400 MSDC_InvertN((kal_uint8*)WPBits32, (kal_uint8*)&tmp, 4);
6401 // configure the controller to the original block length
6402 BitFieldWrite32((kal_uint32*)SDC_CMD, 512, SDC_CMD_BLKLEN);
6403 gSD->mBKLength=blklen;
6404
6405 return NO_ERROR;
6406}
6407
6408// CMD39: Fast IO-used to write and read 8 bit register
6409SDC_CMD_STATUS SD_FastIO_MMC(kal_uint16 rca, kal_bool isWrite, kal_uint8 reg_adrs, kal_uint8 data)
6410{
6411 SDC_CMD_STATUS status;
6412 kal_uint32 arg = 0;
6413
6414 arg = rca << 16;
6415 arg |= isWrite << 15;
6416 arg |= reg_adrs << 8;
6417 arg |= data;
6418
6419 if ((status = SD_SendCmd(SDC_CMD_CMD39_MMC, arg,MSDC_CMD_TIMEOUT)) != NO_ERROR)
6420 return status;
6421
6422 if ((status = SD_CheckStatus()) != NO_ERROR)
6423 return status;
6424
6425 return NO_ERROR;
6426}
6427
6428
6429// Sets the system into interrupt mode (MMC)
6430SDC_CMD_STATUS SD_GoIRQ_MMC(void)
6431{
6432 SDC_CMD_STATUS status;
6433
6434 if ((status = SD_SendCmd(SDC_CMD_CMD40_MMC, SDC_NO_ARG,MSDC_CMD_TIMEOUT)) != NO_ERROR)
6435 return status;
6436
6437 status = *(kal_uint32*)SDC_RESP0;
6438#ifdef MSDC_TRACE_LEVEL2
6439 MD_TRC_MSDC_INFORM_R0(status, __LINE__);
6440#endif
6441
6442 return NO_ERROR;
6443}
6444
6445// Used to set/reset password ,lock/unlock the card and force erase total card.
6446// similiar to a signle block write structure.(CMD42)
6447// max password length = 16
6448SDC_CMD_STATUS SD_LockUnlock(SD_LOCK_OP op, kal_char* Oldpwd, kal_char* Newpwd, kal_uint8 Oldlen, kal_uint8 Newlen)
6449{
6450 SDC_CMD_STATUS status;
6451 kal_uint8 lockbk[SDC_MAX_LOCKBK];
6452 kal_uint32 blklen, *ptr = (kal_uint32*)lockbk, count;
6453
6454 if (Oldlen > 16 || Newlen > 16)
6455 return ERR_ERRORS;
6456
6457 /* save the original block length*/
6458 blklen = gSD->mBKLength;
6459
6460 kal_mem_set(lockbk, 0, SDC_MAX_LOCKBK);
6461
6462 switch (op)
6463 {
6464 case SET_PWD:
6465 lockbk[0] = 0x01;
6466 break;
6467
6468 case CLR_PWD:
6469 lockbk[0] = 0x02;
6470 break;
6471
6472 case LOCK_CARD:
6473 lockbk[0] = 0x04;
6474 break;
6475
6476 case UNLOCK_CARD:
6477 lockbk[0] = 0x00;
6478 break;
6479
6480 case ERASE:
6481 lockbk[0] = 0x08;
6482 break;
6483 }
6484
6485 lockbk[1] = Oldlen + Newlen;
6486 kal_mem_cpy(&lockbk[2], Oldpwd, Oldlen);
6487 kal_mem_cpy(&lockbk[2 + Oldlen], Newpwd, Newlen);
6488
6489 /* set block length */
6490 if (op != ERASE)
6491 {
6492 SD_SetBlength(2 + lockbk[1]);
6493 count = ((lockbk[1] + 2) % sizeof(kal_uint32)) ? ((lockbk[1] + 2) / sizeof(kal_uint32) + 1) :
6494 ((lockbk[1] + 2) / sizeof(kal_uint32));
6495 gSD->mBKNum=1;
6496 blklen=gSD->mBKLength;
6497 gSD->mBKLength = 2 + lockbk[1];
6498 MSDC_WriteReg32(SDC_BLK_NUM,1);
6499 //set to pio mode and clear fifo
6500 BitFieldWrite32((kal_uint32 *)MSDC_CFG, 1, MSDC_CFG_PIO);
6501 gMSDC_Handle->dma_xfer=0;
6502 MSDC_CLR_FIFO();
6503 }
6504 else
6505 {
6506 SD_SetBlength(1);
6507 gSD->mBKNum=1;
6508 blklen=gSD->mBKLength;
6509 gSD->mBKLength = 1;
6510 MSDC_WriteReg32(SDC_BLK_NUM,1);
6511 //set to pio mode and clear fifo
6512 BitFieldWrite32((kal_uint32 *)MSDC_CFG, 1, MSDC_CFG_PIO);
6513 gMSDC_Handle->dma_xfer=0;
6514 MSDC_CLR_FIFO();
6515 count = 1;
6516 }
6517 MSDC_WriteReg32(SDC_BLK_NUM,1);
6518 /* send command */
6519 if ((status = SD_SendCmd(SDC_CMD_CMD42, SDC_NO_ARG,MSDC_CMD_TIMEOUT)) != NO_ERROR)
6520 return status;
6521
6522 /* read R1b */
6523 SD_CheckStatus();
6524 /* clear FIFO */
6525 MSDC_CLR_FIFO();
6526
6527
6528#ifndef DRV_LSD
6529 status=SD_WaitDatRdyOrTo(ptr,count,KAL_TRUE);
6530
6531#endif
6532
6533 /* wait util card has finished programming */
6534 SD_WaitCardNotBusy(MSDC_DATA_TIMEOUT);
6535 // restore the block length back
6536 if (status != NO_ERROR)
6537 {
6538 return gMSDC_Handle->error;
6539 }
6540
6541 // restore the block length back
6542 SD_SetBlength(blklen);
6543 gSD->mBKLength=blklen;
6544 /* check status*/
6545 SD_GetStatus(gSD->mRCA, &status);
6546
6547 if (status & R1_LOCK_UNLOCK_FAILED_24)
6548 return ERR_LOCK_UNLOCK_FAILED;
6549
6550 if ((op == LOCK_CARD) && !(status & R1_CARD_IS_LOCKED_25))
6551 return ERR_LOCK_UNLOCK_FAILED;
6552
6553 if ((op == UNLOCK_CARD) && (status & R1_CARD_IS_LOCKED_25))
6554 return ERR_LOCK_UNLOCK_FAILED;
6555
6556 return NO_ERROR;
6557}
6558
6559// ACMD13: read SD status(512bits = 64bytes single block read)
6560SDC_CMD_STATUS SD_GetSDStatus(kal_uint32* sd_status)
6561{
6562 SDC_CMD_STATUS status;
6563 kal_uint32 blklen;
6564
6565
6566 //if ((status = SD_SetBlength(64)) != NO_ERROR)
6567 // return status;
6568
6569 // send APP_CMD
6570 if ((status = SD_Cmd55(gSD->mRCA)) != NO_ERROR)
6571 return status;
6572 // save the orignial block length
6573 blklen=gSD->mBKLength;
6574 gSD->mBKLength = 64;
6575 MSDC_WriteReg32(SDC_BLK_NUM,1);
6576 MSDC_DEBUG("[SD][%s %d]send acmd13\r\n",__FUNCTION__,__LINE__);
6577
6578 //set to pio mode and clear fifo
6579 BitFieldWrite32((kal_uint32 *)MSDC_CFG, 1, MSDC_CFG_PIO);
6580 gMSDC_Handle->dma_xfer=0;
6581 MSDC_CLR_FIFO();
6582 // send ACMD13
6583 if ((status = SD_SendCmd(SDC_CMD_ACMD13, SDC_NO_ARG,MSDC_CMD_TIMEOUT)) != NO_ERROR)
6584 return status;
6585
6586 //read R1
6587 if ((status = SD_CheckStatus()) != NO_ERROR)
6588 return status;
6589
6590 // read sd status(64bytes = 4x16)
6591 status=SD_WaitDatRdyOrTo(sd_status,64,KAL_FALSE);
6592 if (status !=NO_ERROR)
6593 {
6594 return status;
6595 }
6596 gSD->mBKLength=blklen;
6597 return NO_ERROR;
6598}
6599//ACMD22: get the number of written write blocks(4bytes single block read)
6600SDC_CMD_STATUS SD_GetNumWrittenBlk(kal_uint32* num)
6601{
6602 SDC_CMD_STATUS status;
6603 kal_uint32 blklen, tmp;
6604
6605 // send APP_CMD
6606 if ((status = SD_Cmd55(gSD->mRCA)) != NO_ERROR)
6607 return status;
6608
6609 blklen=gSD->mBKLength;
6610 gSD->mBKLength = 4;
6611 MSDC_WriteReg32(SDC_BLK_NUM,1);
6612 MSDC_DEBUG("[SD][%s %d]send acmd13\r\n",__FUNCTION__,__LINE__);
6613
6614 //set to pio mode and clear fifo
6615 BitFieldWrite32((kal_uint32 *)MSDC_CFG, 1, MSDC_CFG_PIO);
6616 gMSDC_Handle->dma_xfer=0;
6617 MSDC_CLR_FIFO();
6618
6619 // send CMD22
6620 if ((status = SD_SendCmd(SDC_CMD_ACMD22, SDC_NO_ARG,MSDC_CMD_TIMEOUT)) != NO_ERROR)
6621 return status;
6622
6623 //read R1
6624 if ((status = SD_CheckStatus()) != NO_ERROR)
6625 return status;
6626
6627 // read the number of written write blocks(4bytes)
6628
6629 if ((status=SD_WaitDatRdyOrTo(&tmp,4,KAL_FALSE))!=NO_ERROR)
6630 return status;
6631
6632 MSDC_InvertN((kal_uint8*)num, (kal_uint8*)&tmp, 4);
6633
6634 // resotre block length
6635 gSD->mBKLength=blklen;
6636 return NO_ERROR;
6637}
6638
6639#ifdef DRV_MSDC_HW_CONTENTION
6640extern kal_semid dclMsdcArb;
6641#endif
6642
6643void SD_startFastFormat(void)
6644{
6645 #if defined(__AUDIO_DSP_LOWPOWER__)
6646 AUDMA_LOCK(AUDMA_ID_MSDC);
6647 #endif
6648
6649#ifdef DRV_MSDC_HW_CONTENTION
6650 kal_uint32 retAddr;
6651
6652#if defined(__RVCT__)
6653 /* RVCT doesn't support inline assemlber; bypass temporarily */
6654 retAddr = 0;
6655#else /* __RVCT__ */
6656 /* get the return address */
6657 __asm
6658 {
6659 MOV retAddr, lr
6660 }
6661#endif /* __RVCT__ */
6662
6663
6664 if (NULL == dclMsdcArb)
6665 ASSERT(0);
6666
6667 if (kal_query_systemInit() == KAL_FALSE)
6668 {
6669 /*must gain resource here before calling writeSectors*/
6670 kal_take_sem(dclMsdcArb, 1);
6671 SD_setArbRetAddr(retAddr);
6672 SD_setArbThdId((kal_uint32)kal_get_current_thread_ID());
6673 }
6674
6675#endif
6676
6677
6678#ifdef DRV_LSD
6679 LSD_startFastFormat();
6680#elif defined(__DRV_MSDC_FAST_FORMAT__)
6681 gMSDC_Handle->MSDC_fastFormat = KAL_TRUE;
6682#endif
6683}
6684
6685void SD_closeFastFormat(void)
6686{
6687 #ifdef DRV_LSD
6688 LSD_closeFastFormat();
6689 #elif defined(__DRV_MSDC_FAST_FORMAT__)
6690 gMSDC_Handle->MSDC_fastFormat = KAL_FALSE;
6691 #endif
6692
6693 #ifdef DRV_MSDC_HW_CONTENTION
6694
6695 if (kal_query_systemInit() == KAL_FALSE)
6696 {
6697 /*when the semaphore is returned, we set thdId to zero, but not retAddr, we can know that it is released from here*/
6698 SD_setArbThdId(NULL);
6699 kal_give_sem(dclMsdcArb);
6700 }
6701
6702 #endif
6703
6704 #if defined(__AUDIO_DSP_LOWPOWER__)
6705 AUDMA_UNLOCK(AUDMA_ID_MSDC);
6706 #endif
6707
6708}
6709
6710
6711//__attribute__ ((section ("EXT_BOOTLOADER_CODE")))SDC_CMD_STATUS SD_FlushSectors(kal_uint32 startSector, kal_uint32 sectorNum)
6712SDC_CMD_STATUS SD_FlushSectors(kal_uint32 startSector, kal_uint32 sectorNum)
6713{
6714 SDC_CMD_STATUS status;
6715 kal_uint32 sectorMult,maxBlk;
6716
6717 if (gSD->flags & SD_FLAG_HCS_SUPPORT)
6718 sectorMult = 1;
6719 else
6720 sectorMult = SECTOR_SIZE;
6721 maxBlk=gSD->mCSD.capacity /512;
6722 if(0 == sectorNum || sectorNum > maxBlk || startSector > maxBlk){
6723 //ASSERT(0);
6724 status = STATUS_INVALID_CTRL_DATA;
6725 return status;
6726 }
6727
6728 /*check that ending block should be smaller than maximum block number*/
6729 if((startSector + sectorNum - 1) > maxBlk){
6730 //ASSERT(0);
6731 status = STATUS_INVALID_CTRL_DATA;
6732 return status;
6733 }
6734 MSDC_PDNControl(KAL_FALSE);
6735
6736 // there are differences between SD and MMC
6737 // tag erase start(CMD32)
6738 if ((status = SD_EraseCmdClass(SDC_CMD_CMD32, sectorMult * startSector)) != NO_ERROR)
6739 {
6740 goto ErrorExit;
6741 }
6742
6743 // tag erase end(CMD33)
6744 if ((status = SD_EraseCmdClass(SDC_CMD_CMD33, sectorMult * (startSector + sectorNum - 1))) != NO_ERROR)
6745 {
6746 goto ErrorExit;
6747 }
6748
6749 // erase...(CMD38)
6750 if ((status = SD_EraseCmdClass(SDC_CMD_CMD38, 0)) != NO_ERROR)
6751 {
6752 goto ErrorExit;
6753 }
6754
6755ErrorExit:
6756 MSDC_PDNControl(KAL_TRUE);
6757 return status;
6758}
6759
6760#ifdef IC_MODULE_TEST
6761
6762kal_bool MSDC_ModuleTest_Report(void)
6763{
6764
6765 SDC_CMD_STATUS status;
6766
6767 if (gMSDC_Handle->mIsInitialized == KAL_FALSE)
6768 return KAL_FALSE;
6769
6770 MSDC_PDNControl(KAL_FALSE);
6771
6772 gMSDC_Handle->mIsInitialized = KAL_TRUE;
6773 gMSDC_Handle->trySingleLine = KAL_TRUE;
6774
6775 status = SD_Initialize();
6776
6777 if (status == NO_ERROR)
6778 return KAL_TRUE;
6779 else
6780 return KAL_FALSE;
6781
6782}
6783#endif
6784
6785#else
6786#ifdef DRV_LSD
6787T_SDC_HANDLE gSD_blk[SD_NUM];
6788T_SDC_HANDLE *gSD = gSD_blk;
6789#endif
6790#endif // defined(__MSDC_SD_MMC__)
6791
6792#ifdef MSDC_DEBUG
6793
6794#define TST_ADRS 512*12
6795kal_uint32 SD_MMC_Test(void)
6796{
6797
6798 return 0;
6799
6800}
6801#endif // FPGA_DEBUG
6802
6803#endif//!defined(__UBL__) || defined(__CARD_DOWNLOAD__) || defined(__EMMC_BOOTING__)
6804
6805#else //DRV_MSDC_OFF
6806#include "kal_public_api.h" //MSBB change #include "kal_release.h"
6807#include "kal_general_types.h"
6808//#include "btif_sw.h"
6809#include "kal_public_api.h"
6810#include "kal_internal_api.h"
6811#include "kal_public_defs.h"
6812
6813//#include "gpt_sw.h"
6814#include "drv_comm.h"
6815#include "reg_base.h"
6816#include "msdc_def.h"
6817#include "sd_def.h"
6818#include "upll_ctrl.h"
6819//#include "Drv_trc.h"
6820#ifdef DCL_MSDC_INTERFACE
6821#include "dcl.h"
6822void SD_dummyAPI(void) {}
6823SDC_CMD_STATUS SD_SetBlength(kal_uint32 BKLength) {}
6824SDDriver_t sd_driver_MTK1 =
6825{
6826 (DCL_SINGLE_BLK_RD)SD_dummyAPI,
6827 (DCL_MUL_BLK_RD)SD_dummyAPI,
6828 (DCL_SINGLE_BLK_WR)SD_dummyAPI,
6829 (DCL_MUL_BLK_WR)SD_dummyAPI,
6830 (DCL_SD_INITITALIZE)SD_dummyAPI,
6831 (DCL_SET_PRE_ERASE_CNT)SD_dummyAPI,
6832 (DCL_SD_SET_CALLBACK)SD_dummyAPI,
6833 (DCL_SET_READ_TEST_FLAG)SD_dummyAPI,
6834 (DCL_SD_READ_TEST)SD_dummyAPI,
6835 (DCL_SD_SET_UPLL_CLOCK_TEST)SD_dummyAPI,
6836 (DCL_SD_ERASE_BLK)SD_dummyAPI,
6837 (DCL_GPD_MUL_BLK_RD)SD_dummyAPI,
6838 (DCL_GPD_MUL_BLK_WR)SD_dummyAPI,
6839};
6840#endif //DCL_MSDC_INTERFACE
6841
6842void SD_startFastFormat(void) {}
6843void SD_closeFastFormat(void) {}
6844T_SDC_HANDLE gSD_blk[SD_NUM];
6845T_SDC_HANDLE *gSD = gSD_blk;
6846
6847#if defined( __MSDC_BASIC_LOAD__) || defined( __MEUT__)
6848kal_uint32 msdc_ReadTestFlag;
6849#endif
6850
6851#endif //DRV_MSDC_OFF
6852
6853