mirror of
https://github.com/CTCaer/hekate.git
synced 2024-11-22 18:06:40 +00:00
[sdmmc] Fix Sandisk U1 fast power cycle
Some Sandisk U1 sd cards do not behave nicely if they power cycle too fast. A min 100ms wait, is enough to mitigate that. Fortunately, because of how the code paths are structured, this was never hit.
This commit is contained in:
parent
36d2da5d79
commit
25f6e91677
5 changed files with 17 additions and 3 deletions
|
@ -45,6 +45,7 @@ void set_default_configuration()
|
|||
h_cfg.autonogc = 1;
|
||||
h_cfg.sept_run = EMC(EMC_SCRATCH0) & EMC_SEPT_RUN;
|
||||
h_cfg.rcm_patched = true;
|
||||
h_cfg.sd_timeoff = 0;
|
||||
}
|
||||
|
||||
int create_config_entry()
|
||||
|
|
|
@ -35,6 +35,7 @@ typedef struct _hekate_config
|
|||
u32 errors;
|
||||
int sept_run;
|
||||
bool rcm_patched;
|
||||
u32 sd_timeoff;
|
||||
} hekate_config;
|
||||
|
||||
typedef enum
|
||||
|
|
|
@ -96,7 +96,7 @@ static u32 _parity32_even(u32 *words, u32 count)
|
|||
lo = ((x & 0xf) ^ (x >> 4)) & 3;
|
||||
hi = ((x & 0xf) ^ (x >> 4)) >> 2;
|
||||
x = hi ^ lo;
|
||||
|
||||
|
||||
return (x & 1) ^ (x >> 1);
|
||||
}
|
||||
|
||||
|
|
|
@ -19,6 +19,7 @@
|
|||
#include "sdmmc.h"
|
||||
#include "mmc.h"
|
||||
#include "sd.h"
|
||||
#include "../config/config.h"
|
||||
#include "../gfx/gfx.h"
|
||||
#include "../mem/heap.h"
|
||||
#include "../utils/util.h"
|
||||
|
@ -26,6 +27,8 @@
|
|||
//#define DPRINTF(...) gfx_printf(__VA_ARGS__)
|
||||
#define DPRINTF(...)
|
||||
|
||||
extern hekate_config h_cfg;
|
||||
|
||||
static inline u32 unstuff_bits(u32 *resp, u32 start, u32 size)
|
||||
{
|
||||
const u32 mask = (size < 32 ? 1 << size : 0) - 1;
|
||||
|
@ -833,6 +836,7 @@ int _sd_storage_enable_highspeed_low_volt(sdmmc_storage_t *storage, u32 type, u8
|
|||
switch (type)
|
||||
{
|
||||
case 11:
|
||||
// Fall through if not supported.
|
||||
if (buf[13] & SD_MODE_UHS_SDR104)
|
||||
{
|
||||
type = 11;
|
||||
|
@ -841,7 +845,6 @@ int _sd_storage_enable_highspeed_low_volt(sdmmc_storage_t *storage, u32 type, u8
|
|||
storage->csd.busspeed = 104;
|
||||
break;
|
||||
}
|
||||
//Fall through.
|
||||
case 10:
|
||||
if (buf[13] & SD_MODE_UHS_SDR50)
|
||||
{
|
||||
|
@ -878,7 +881,7 @@ int _sd_storage_enable_highspeed_high_volt(sdmmc_storage_t *storage, u8 *buf)
|
|||
if (!_sd_storage_switch_get(storage, buf))
|
||||
return 0;
|
||||
//gfx_hexdump(0, (u8 *)buf, 64);
|
||||
if (!(buf[13] & 2))
|
||||
if (!(buf[13] & SD_MODE_HIGH_SPEED))
|
||||
return 1;
|
||||
|
||||
if (!_sd_storage_enable_highspeed(storage, 1, buf))
|
||||
|
@ -1012,6 +1015,11 @@ static void _sd_storage_parse_csd(sdmmc_storage_t *storage)
|
|||
int sdmmc_storage_init_sd(sdmmc_storage_t *storage, sdmmc_t *sdmmc, u32 id, u32 bus_width, u32 type)
|
||||
{
|
||||
int is_version_1 = 0;
|
||||
|
||||
// Some cards (Sandisk U1), do not like a fast power cycle. Wait min 100ms.
|
||||
u32 sd_poweroff_time = (u32)get_tmr_ms() - h_cfg.sd_timeoff;
|
||||
if (id == SDMMC_1 && (sd_poweroff_time < 100))
|
||||
msleep(100 - sd_poweroff_time);
|
||||
|
||||
memset(storage, 0, sizeof(sdmmc_storage_t));
|
||||
storage->sdmmc = sdmmc;
|
||||
|
|
|
@ -19,6 +19,7 @@
|
|||
|
||||
#include "mmc.h"
|
||||
#include "sdmmc.h"
|
||||
#include "../config/config.h"
|
||||
#include "../gfx/gfx.h"
|
||||
#include "../power/max7762x.h"
|
||||
#include "../soc/clock.h"
|
||||
|
@ -31,6 +32,8 @@
|
|||
//#define DPRINTF(...) gfx_printf(__VA_ARGS__)
|
||||
#define DPRINTF(...)
|
||||
|
||||
extern hekate_config h_cfg;
|
||||
|
||||
/*! SCMMC controller base addresses. */
|
||||
static const u32 _sdmmc_bases[4] = {
|
||||
0x700B0000,
|
||||
|
@ -1037,6 +1040,7 @@ void sdmmc_end(sdmmc_t *sdmmc)
|
|||
{
|
||||
gpio_output_enable(GPIO_PORT_E, GPIO_PIN_4, GPIO_OUTPUT_DISABLE);
|
||||
max77620_regulator_enable(REGULATOR_LDO2, 0);
|
||||
h_cfg.sd_timeoff = get_tmr_ms(); // Some sandisc U1 cards need 100ms for a power cycle.
|
||||
msleep(1); // To power cycle min 1ms without power is needed.
|
||||
}
|
||||
|
||||
|
|
Loading…
Reference in a new issue