@@ -2,7 +2,7 @@ use anyhow::{Context as _, bail};
22use embedded_sdmmc:: sdcard:: argument:: { Acmd6 , Cmd7 , Cmd9 , Cmd13 , OcrLower , VoltageSuppliedSelect } ;
33use embedded_sdmmc:: sdcard:: mock:: SdCardMock ;
44use embedded_sdmmc:: sdcard:: response:: { self , R1 , R3 , R6 , R7 } ;
5- use embedded_sdmmc:: sdcard:: { AcmdId , CmdId , argument} ;
5+ use embedded_sdmmc:: sdcard:: { AcmdId , CardType , CmdId , argument} ;
66use embedded_sdmmc:: sdcard:: { cid:: Cid , csd:: Csd } ;
77
88/// Negotiated as part of ACMD41 during SD card initialization.
@@ -35,7 +35,7 @@ impl SdCardUninitialized {
3535 self . 0 . insert_command ( CmdId :: CMD0_GoIdleState , 0 ) ;
3636
3737 // Voltage level negotiation. Send CMD8 first.
38- self . 0 . insert_command (
38+ let status = self . 0 . insert_command (
3939 CmdId :: CMD8_SendIfCond ,
4040 argument:: Cmd8 :: ZERO
4141 . with_voltage_supplied (
@@ -44,42 +44,57 @@ impl SdCardUninitialized {
4444 . with_check_pattern ( 0xAA )
4545 . raw_value ( ) ,
4646 ) ;
47-
48- let r7 = R7 :: new_with_raw_value ( self . 0 . read_reply_u32 ( ) ) ;
49- if r7
50- . voltage_accepted ( )
51- . is_ok_and ( |val| val != VoltageSuppliedSelect :: _2_7To3_6V)
52- {
53- bail ! ( "CMD8 reply R7: Voltage not accepted" ) ;
54- }
55- if r7. echo_check_pattern ( ) != 0xAA {
56- bail ! ( "CMD8 reply R7: Check pattern missmatch" ) ;
57- }
47+ let responded_to_cmd8 = !status. timeout ( ) ;
48+
49+ let hcs = if responded_to_cmd8 {
50+ let r7 = R7 :: new_with_raw_value ( self . 0 . read_reply_u32 ( ) ) ;
51+ if r7
52+ . voltage_accepted ( )
53+ . is_ok_and ( |val| val != VoltageSuppliedSelect :: _2_7To3_6V)
54+ {
55+ bail ! ( "CMD8 reply R7: Voltage not accepted" ) ;
56+ }
57+ if r7. echo_check_pattern ( ) != 0xAA {
58+ bail ! ( "CMD8 reply R7: Check pattern missmatch" ) ;
59+ }
60+ embedded_sdmmc:: sdcard:: argument:: HostCapacitySupport :: SdhcOrSdxc
61+ } else {
62+ embedded_sdmmc:: sdcard:: argument:: HostCapacitySupport :: SdscOnly
63+ } ;
5864
5965 // Now send ACMD41.
6066 self . 0 . insert_acmd (
6167 AcmdId :: ACMD41_SdSendOpCond ,
6268 argument:: Acmd41 :: builder ( )
63- . with_host_capacity_support (
64- embedded_sdmmc:: sdcard:: argument:: HostCapacitySupport :: SdhcOrSdxc ,
65- )
69+ . with_host_capacity_support ( hcs)
6670 . with_fast_boot ( false )
6771 . with_xpc ( embedded_sdmmc:: sdcard:: argument:: PowerControl :: MaximumPerformance )
6872 . with_s18r ( false )
6973 . with_ocr ( VOLTAGE_LEVEL_CAPABILITIES )
7074 . build ( )
7175 . raw_value ( ) ,
7276 ) ;
77+ let mut r3;
7378 loop {
7479 // Now poll until the card initialization is complete. In real driver code, timeout
7580 // handling or an upper polling limit might be a good idea.
7681 self . 0 . insert_acmd ( AcmdId :: ACMD41_SdSendOpCond , 0 ) ;
77- let r3 = R3 :: new_with_raw_value ( self . 0 . read_reply_u32 ( ) ) ;
82+ r3 = R3 :: new_with_raw_value ( self . 0 . read_reply_u32 ( ) ) ;
7883 if r3. initialization_complete ( ) {
7984 break ;
8085 }
8186 }
8287
88+ let card_type = if responded_to_cmd8 {
89+ if r3. card_capacity_status ( ) {
90+ CardType :: SdhcSdxc
91+ } else {
92+ CardType :: SD2
93+ }
94+ } else {
95+ CardType :: SD1
96+ } ;
97+
8398 // Retrieve and cache the CID. This puts it into identification mode.
8499 self . 0 . insert_command ( CmdId :: CMD2_AllSendCid , 0 ) ;
85100 let cid_raw = self . 0 . read_reply_u128 ( ) ;
@@ -123,6 +138,7 @@ impl SdCardUninitialized {
123138 ) ;
124139
125140 Ok ( SdCard {
141+ card_type,
126142 cid,
127143 csd,
128144 rca,
@@ -133,6 +149,7 @@ impl SdCardUninitialized {
133149
134150#[ derive( Debug ) ]
135151pub struct SdCard {
152+ card_type : CardType ,
136153 cid : Cid ,
137154 csd : Csd ,
138155 rca : u16 ,
@@ -143,13 +160,15 @@ pub struct SdCard {
143160const MOCK_SD_RCA : u16 = 1 ;
144161
145162fn main ( ) -> Result < ( ) , anyhow:: Error > {
146- let sd_mock = SdCardMock :: new ( MOCK_SD_RCA ) ;
163+ let sd_mock = SdCardMock :: new ( CardType :: SdhcSdxc , MOCK_SD_RCA ) ;
147164 let sd_card_uninit = SdCardUninitialized :: new ( sd_mock) ;
148165 let sd_card = sd_card_uninit
149166 . initialize ( )
150167 . context ( "failed to initialize SD card" ) ?;
151168 println ! ( "SD card initialized successfully" , ) ;
152169 println ! ( "--------" ) ;
170+ println ! ( "Card Type: {:?}" , sd_card. card_type) ;
171+ println ! ( "--------" ) ;
153172 println ! ( "Relative Card Address: {}" , sd_card. rca) ;
154173 println ! ( "--------" ) ;
155174 println ! ( "CSD: {:?}" , sd_card. csd) ;
0 commit comments