---------------------------------------------------------------------------- -- Copyright (C) 2016-2017, AdaCore -- -- Redistribution and use in source and binary forms, with or without -- modification, are permitted provided that the following conditions are -- met: -- 1. Redistributions of source code must retain the above copyright -- notice, this list of conditions and the following disclaimer. -- 2. Redistributions in binary form must reproduce the above copyright -- notice, this list of conditions and the following disclaimer in -- the documentation and/or other materials provided with the -- distribution. -- 3. Neither the name of STMicroelectronics nor the names of its -- contributors may be used to endorse or promote products derived -- from this software without specific prior written permission. -- -- THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS -- "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT -- LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR -- A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT -- HOLDER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, -- SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT -- LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, -- DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY -- THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT -- (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE -- OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. -- -- ----------------------------------------------------------------------------
Acmd_Desc : constant ACmd_Desc_Array :=
  (SD_App_Set_Bus_Width => (Cmd => SD_App_Set_Bus_Width,
                            Rsp => Rsp_R1,
                            Tfr => Tfr_No),
   SD_App_Send_Op_Cond  => (Cmd => SD_App_Send_Op_Cond,
                            Rsp => Rsp_R3,
                            Tfr => Tfr_No),
   SD_App_Send_SCR      => (Cmd => SD_App_Send_SCR,
                            Rsp => Rsp_R1,
                            Tfr => Tfr_Read),
   others               => (Cmd => 0,
                            Rsp => Rsp_Invalid,
                            Tfr => Tfr_Invalid));
type ACmd_Desc_Array is array (SD_Specific_Command) of Cmd_Desc_Type;
All_Send_CID         : constant SD_Command := 2;
App_Cmd              : constant SD_Command := 55;
type Card_Identification_Data_Register is record
   Manufacturer_ID       : UInt8;
   OEM_Application_ID    : String (1 .. 2);
   Product_Name          : String (1 .. 5);
   Product_Revision      : Card_Revision;
   Product_Serial_Number : UInt32;
   Reserved_1            : UInt8;
   Manufacturing_Date    : Manufacturing_Date_Type;
   CID_CRC               : UInt8;
   Reserved_2            : UInt8;
end record;
Always 1
type Card_Information is record
   SD_CSD          : Card_Specific_Data_Register;
   SD_CID          : Card_Identification_Data_Register;
   Card_Capacity   : UInt64;
   Card_Block_Size : UInt32;
   RCA             : UInt16;
   Card_Type       : Supported_SD_Memory_Cards :=
                       STD_Capacity_SD_Card_V1_1;
end record;
SD relative card address
type Card_Revision is record
   Major : UInt4;
   Minor : UInt4;
end record with Pack;
type Card_Specific_Data_Register is record
   CSD_Structure                    : UInt8;
   System_Specification_Version     : UInt8;
   Reserved                         : UInt8;
   Data_Read_Access_Time_1          : UInt8;
   Data_Read_Access_Time_2          : UInt8;
   Max_Data_Transfer_Rate           : UInt8;
   Card_Command_Class               : UInt16;
   Max_Read_Data_Block_Length       : UInt8;
   Partial_Block_For_Read_Allowed   : Boolean;
   Write_Block_Missalignment        : Boolean;
   Read_Block_Missalignment         : Boolean;
   DSR_Implemented                  : Boolean;
   Reserved_2                       : UInt8;
   Device_Size                      : UInt32;
   Max_Read_Current_At_VDD_Min      : UInt8;
   Max_Read_Current_At_VDD_Max      : UInt8;
   Max_Write_Current_At_VDD_Min     : UInt8;
   Max_Write_Current_At_VDD_Max     : UInt8;
   Device_Size_Multiplier           : UInt8;
   Erase_Group_Size                 : UInt8;
   Erase_Group_Size_Multiplier      : UInt8;
   Write_Protect_Group_Size         : UInt8;
   Write_Protect_Group_Enable       : Boolean;
   Manufacturer_Default_ECC         : UInt8;
   Write_Speed_Factor               : UInt8;
   Max_Write_Data_Block_Length      : UInt8;
   Partial_Blocks_For_Write_Allowed : Boolean;
   Reserved_3                       : UInt8;
   Content_Protection_Application   : Boolean;
   File_Format_Group                : Boolean;
   Copy_Flag                        : Boolean;
   Permanent_Write_Protection       : Boolean;
   Temporary_Write_Protection       : Boolean;
   File_Format                      : UInt8;
   ECC_Code                         : UInt8;
   CSD_CRC                          : UInt8;
   Reserved_4                       : UInt8;
end record;
In CLK Cycles
Always 1
Clr_Write_Prot       : constant SD_Command := 29;
Cmd_Desc : constant Cmd_Desc_Array :=
  (Go_Idle_State      => (Cmd => Go_Idle_State,
                          Rsp => Rsp_No,
                          Tfr => Tfr_No),
   Send_Op_Cond       => (Cmd => Send_Op_Cond,
                          Rsp => Rsp_R3,
                          Tfr => Tfr_No),
   All_Send_CID       => (Cmd => All_Send_CID,
                          Rsp => Rsp_R2,
                          Tfr => Tfr_No),
   Send_Relative_Addr => (Cmd => Send_Relative_Addr,
                          Rsp => Rsp_R3,
                          Tfr => Tfr_No),
   Switch_Func        => (Cmd => Switch_Func,
                          Rsp => Rsp_R1,
                          Tfr => Tfr_Read),
   Select_Card        => (Cmd => Select_Card,
                          Rsp => Rsp_R1B,
                          Tfr => Tfr_No),
   Send_If_Cond       => (Cmd => Send_If_Cond,
                          Rsp => Rsp_R7,
                          Tfr => Tfr_No),
   Send_CSD           => (Cmd => Send_CSD,
                          Rsp => Rsp_R2,
                          Tfr => Tfr_No),
   Send_CID           => (Cmd => Send_CID,
                          Rsp => Rsp_R2,
                          Tfr => Tfr_No),
   Stop_Transmission  => (Cmd => Stop_Transmission,
                          Rsp => Rsp_R1,
                          Tfr => Tfr_No),
   Read_Single_Block  => (Cmd => Read_Single_Block,
                          Rsp => Rsp_R1,
                          Tfr => Tfr_Read),
   Read_Multi_Block   => (Cmd => Read_Multi_Block,
                          Rsp => Rsp_R1,
                          Tfr => Tfr_Read_Multi),
   Send_Status        => (Cmd => Send_Status,
                          Rsp => Rsp_R1,
                          Tfr => Tfr_No),
   Set_Blocklen       => (Cmd => Set_Blocklen,
                          Rsp => Rsp_R1,
                          Tfr => Tfr_No),
   App_Cmd            => (Cmd => App_Cmd,
                          Rsp => Rsp_R1,
                          Tfr => Tfr_No),
   Write_Single_Block => (Cmd => Write_Single_Block,
                          Rsp => Rsp_R1,
                          Tfr => Tfr_Write),
   Write_Multi_Block  => (Cmd => Write_Multi_Block,
                          Rsp => Rsp_R1,
                          Tfr => Tfr_Write_Multi),
   others             => (Cmd => 0,
                          Rsp => Rsp_Invalid,
                          Tfr => Tfr_Invalid));
type Cmd_Desc_Array is array (SD_Command) of Cmd_Desc_Type;
type Cmd_Desc_Type is record
   Cmd : SD_Command;
   Rsp : Rsp_Kind;
   Tfr : Tfr_Kind;
end record;
procedure Delay_Milliseconds
  (This   : SDMMC_Driver;
   Amount : Natural)
Do not use directly 'delay until' so that this package can still be used with the zfp profile
Deselect_Card        : constant SD_Command := 7;
Erase                : constant SD_Command := 38;
Erase_Grp_End        : constant SD_Command := 36;
Erase_Grp_Start      : constant SD_Command := 35;
Fast_IO              : constant SD_Command := 39;
Gen_Cmd              : constant SD_Command := 56;
Go_Idle_State        : constant SD_Command := 0;
Go_Inactive_State    : constant SD_Command := 15;
Go_IRQ_State         : constant SD_Command := 40;
HS_Bustest_Read      : constant SD_Command := 14;
HS_Bustest_Write     : constant SD_Command := 19;
Lock_Unlock          : constant SD_Command := 42;
type Manufacturing_Date_Type is record
   Year : Manufacturing_Year;
   Month : Manufacturing_Month;
end record;
type Manufacturing_Month is
  (January,
   February,
   March,
   April,
   May,
   June,
   July,
   August,
   September,
   October,
   November,
   December) with Size => 4;
type Manufacturing_Year is range 2000 .. 2255;
Prog_CID             : constant SD_Command := 26;
Prog_CSD             : constant SD_Command := 27;
procedure Read_Cmd
  (This   : in out SDMMC_Driver;
   Cmd    : Cmd_Desc_Type;
   Arg    : UInt32;
   Buf    : out UInt32_Array;
   Status : out SD_Error)
Read data command
Read_Dat_Until_Stop  : constant SD_Command := 11;
Read_Multi_Block     : constant SD_Command := 18;
procedure Read_Rsp136
  (This           : in out SDMMC_Driver;
   W0, W1, W2, W3 : out UInt32)
Read the 128 interesting bits of the last 136 bit response. W0 is the MSB, W3 the LSB Cannot fail.
procedure Read_Rsp48
  (This : in out SDMMC_Driver;
   Rsp  : out UInt32)
Read the 32 interesting bits of the last 48bits response (start bit, transmission bit, command index, crc and end bit are discarded). Cannot fail.
Read_Single_Block    : constant SD_Command := 17;
procedure Reset
  (This   : in out SDMMC_Driver;
   Status : out SD_Error)
Initialize the driver, enable clocking.
type Rsp_Kind is
  (Rsp_Invalid,
   Rsp_No,
   Rsp_R1, Rsp_R1B, Rsp_R2, Rsp_R3, Rsp_R6, Rsp_R7
  );
Response format
Unknown/invalid command
No response.
SD_App_Change_Secure_Area          : constant SD_Specific_Command := 49;
SD_App_Get_CER_RES1                : constant SD_Specific_Command := 48;
SD_App_Get_CER_RN2                 : constant SD_Specific_Command := 46;
SD_App_Get_MID                     : constant SD_Specific_Command := 44;
SD_App_Get_MKB                     : constant SD_Specific_Command := 43;
SD_App_Secure_Erase                : constant SD_Specific_Command := 38;
SD_App_Secure_Read_Multi_Block     : constant SD_Specific_Command := 18;
SD_App_Secure_Write_Multi_Block    : constant SD_Specific_Command := 25;
SD_App_Send_Num_Write_Blocks       : constant SD_Specific_Command := 22;
SD_App_Send_Op_Cond                : constant SD_Specific_Command := 41;
SD_App_Send_SCR                    : constant SD_Specific_Command := 51;
SD_App_Set_Bus_Width               : constant SD_Specific_Command := 6;
SD_App_Set_CER_RES2                : constant SD_Specific_Command := 47;
SD_App_Set_CER_RN1                 : constant SD_Specific_Command := 45;
SD_App_Set_Write_Block_Erase_Count : constant SD_Specific_Command := 23;
SD_App_Status                      : constant SD_Specific_Command := 13;
type SD_Command is new UInt6;
SD_Erase_Grp_End     : constant SD_Command := 33;
SD_Erase_Grp_Start   : constant SD_Command := 32;
type SD_Error is
  (OK,
   Error,
   Timeout_Error,
   Command_Timeout_Error,
   Unsupported_Card,
   Rx_Overrun,
   Tx_Underrun,
   Request_Not_Applicable,
   CRC_Check_Fail,
   Illegal_Cmd,
   Address_Out_Of_Range,
   Address_Missaligned,
   Block_Length_Error,
   Erase_Seq_Error,
   Bad_Erase_Parameter,
   Write_Protection_Violation,
   Lock_Unlock_Failed,
   Card_ECC_Failed,
   Card_ECC_Disabled,
   CC_Error,
   General_Unknown_Error,
   Stream_Read_Underrun,
   Stream_Write_Underrun,
   CID_CSD_Overwrite,
   WP_Erase_Skip,
   Erase_Reset,
   AKE_SEQ_Error,
   Invalid_Voltage_Range,
   Startbit_Not_Detected,
   DMA_Alignment_Error);
subtype SD_Specific_Command is SD_Command;
type SDCard_Configuration_Register is record
   SCR_Structure         : UInt8;
   SD_Spec               : UInt8;
   Data_Stat_After_Erase : UInt8;
   SD_Security           : UInt8;
   SD_Bus_Widths         : UInt8;
   SD_Spec3              : Boolean;
   Ex_Security           : UInt8;
   SD_Spec4              : Boolean;
   Reserved_1            : UInt8;
   CMD_Support           : UInt8;
   Reserved_2            : UInt32;
end record;
type SDMMC_Driver is limited interface;
SDMMC_Send_Op_Cond   : constant SD_Command := 5;
Select_Card          : constant SD_Command := 7;
procedure Send_ACmd
  (This   : in out SDMMC_Driver'Class;
   Cmd    : SD_Specific_Command;
   Rca    : UInt16;
   Arg    : UInt32;
   Status : out SD_Error)
Send application specific command
Send_CID             : constant SD_Command := 10;
procedure Send_Cmd
  (This   : in out SDMMC_Driver'Class;
   Cmd    : SD_Command;
   Arg    : UInt32;
   Status : out SD_Error)
Wrapper for Send_Cmd using a generic command.
procedure Send_Cmd
  (This   : in out SDMMC_Driver;
   Cmd    : Cmd_Desc_Type;
   Arg    : UInt32;
   Status : out SD_Error)
Send a command (without data transfer) and wait for result.
Send_CSD             : constant SD_Command := 9;
Send_If_Cond         : constant SD_Command := 8;
Send_Op_Cond         : constant SD_Command := 1;
Only for MMC
Send_Relative_Addr   : constant SD_Command := 3;
Send_Status          : constant SD_Command := 13;
Send_Write_Prot      : constant SD_Command := 30;
Set_Block_Count      : constant SD_Command := 23;
Set_Blocklen         : constant SD_Command := 16;
procedure Set_Bus_Size
  (This : in out SDMMC_Driver;
   Mode : Wide_Bus_Mode)
Set host bus size; the command must have been set to the card.
procedure Set_Clock
  (This : in out SDMMC_Driver;
   Freq : Natural)
Set clock frequency.
Set_DSR              : constant SD_Command := 4;
Set_Write_Prot       : constant SD_Command := 28;
Stop_Transmission    : constant SD_Command := 12;
type Supported_SD_Memory_Cards is
  (STD_Capacity_SD_Card_V1_1,
   STD_Capacity_SD_Card_v2_0,
   High_Capacity_SD_Card,
   Multimedia_Card,
   Secure_Digital_IO_Card,
   High_Speed_Multimedia_Card,
   Secure_Digital_IO_Combo_Card,
   High_Capacity_MMC_Card);
Switch_Func          : constant SD_Command := 6;
type Tfr_Kind is
  (Tfr_Invalid, Tfr_No,
   Tfr_Read, Tfr_Write,
   Tfr_Read_Multi, Tfr_Write_Multi);
Transfer
type Wide_Bus_Mode is
  (
   Wide_Bus_1B,
   Wide_Bus_4B,
   Wide_Bus_8B)
  with Size => 2;
4-wide bus mode: SDMMC_D[3:0] used.
8-wide bus mode: SDMMC_D[7:0] used.
Write_Dat_Until_Stop : constant SD_Command := 20;
Write_Multi_Block    : constant SD_Command := 25;
Write_Single_Block   : constant SD_Command := 24;