/** * \brief Application entry point. * * \return Unused (ANSI-C compatibility). */ int main(void) { uint8_t slot = 0; sd_mmc_err_t err; system_init(); delay_init(); cdc_uart_init(); irq_initialize_vectors(); cpu_irq_enable(); time_tick_init(); // Initialize SD MMC stack sd_mmc_init(); printf("\x0C\n\r-- SD/MMC Card Example --\n\r"); printf("-- Compiled: %s %s --\n\r", __DATE__, __TIME__); while (1) { if (slot == sd_mmc_nb_slot()) { slot = 0; } printf("Please plug an SD/MMC card in slot %d.\n\r", slot+1); // Wait for a card and ready do { err = sd_mmc_check(slot); if ((SD_MMC_ERR_NO_CARD != err) && (SD_MMC_INIT_ONGOING != err) && (SD_MMC_OK != err)) { printf("Card install FAILED\n\r"); printf("Please unplug and re-plug the card.\n\r"); while (SD_MMC_ERR_NO_CARD != sd_mmc_check(slot)) { } } } while (SD_MMC_OK != err); // Display basic card information main_display_info_card(slot); /* Test the card */ if (sd_mmc_get_type(slot) & (CARD_TYPE_SD | CARD_TYPE_MMC)) { // SD/MMC Card R/W main_test_memory(slot); } printf("Test finished, please unplugged the card.\n\r"); while (SD_MMC_OK == sd_mmc_check(slot)) { } slot++; } }
/* Changes the encryption level of the drive. If encrypt is true: encrypt drive, else decrypt */ uint8_t sd_change_encryption(uint8_t slot, bool encrypt, bool change_key, uint8_t *old_passwd, uint8_t *new_passwd) { sd_mmc_err_t err; uint32_t i, nb_blocks; encrypt_config_t *config_ptr = NULL; security_get_config(&config_ptr); if ((encrypt == config_ptr->encryption_level) && !change_key) return CTRL_GOOD; if (change_key) { sha2(old_passwd, MAX_PASS_LENGTH, old_hash_cipher_key, 0); sha2(new_passwd, MAX_PASS_LENGTH, new_hash_cipher_key, 0); } if (old_hash_cipher_key == new_hash_cipher_key) return CTRL_GOOD; do { err = sd_mmc_check(slot); if ((SD_MMC_ERR_NO_CARD != err) && (SD_MMC_INIT_ONGOING != err) && (SD_MMC_OK != err)) { while (SD_MMC_ERR_NO_CARD != sd_mmc_check(slot)) { } } } while (SD_MMC_OK != err); nb_blocks = sd_mmc_get_capacity(slot) * (1024 / SD_MMC_BLOCK_SIZE); for (i = 0; i < nb_blocks / SD_BLOCKS_PER_ACCESS; ++i) { if (SD_MMC_OK != sd_mmc_init_read_blocks(slot, i, SD_BLOCKS_PER_ACCESS)) return CTRL_FAIL; if (SD_MMC_OK != sd_mmc_start_read_blocks(src_buf, SD_BLOCKS_PER_ACCESS)) return CTRL_FAIL; if (SD_MMC_OK != sd_mmc_wait_end_of_read_blocks()) return CTRL_FAIL; aes_set_key(&AVR32_AES, (unsigned int *)old_hash_cipher_key); ram_aes_ram(change_key ? false : encrypt, SD_MMC_BLOCK_SIZE * SD_BLOCKS_PER_ACCESS / sizeof(unsigned int), (unsigned int *)src_buf, (unsigned int *)dest_buf); if (change_key) { aes_set_key(&AVR32_AES, (unsigned int *)new_hash_cipher_key); ram_aes_ram(true, SD_MMC_BLOCK_SIZE * SD_BLOCKS_PER_ACCESS / sizeof(unsigned int), (unsigned int *)dest_buf, (unsigned int *)src_buf); } if (SD_MMC_OK != sd_mmc_init_write_blocks(slot, i, SD_BLOCKS_PER_ACCESS)) return CTRL_FAIL; if (SD_MMC_OK != sd_mmc_start_write_blocks(src_buf, SD_BLOCKS_PER_ACCESS)) return CTRL_FAIL; if (SD_MMC_OK != sd_mmc_wait_end_of_write_blocks()) return CTRL_FAIL; } return CTRL_GOOD; }
Ctrl_status sd_mmc_test_unit_ready(uint8_t slot) { switch (sd_mmc_check(slot)) { case SD_MMC_OK: if (sd_mmc_ejected[slot]) { return CTRL_NO_PRESENT; } if (sd_mmc_get_type(slot) & (CARD_TYPE_SD | CARD_TYPE_MMC)) { return CTRL_GOOD; } // It is not a memory card return CTRL_NO_PRESENT; case SD_MMC_INIT_ONGOING: return CTRL_BUSY; case SD_MMC_ERR_NO_CARD: sd_mmc_ejected[slot] = false; return CTRL_NO_PRESENT; default: return CTRL_FAIL; } }
/** * \brief Initialize SD/MMC storage. */ static void init_storage(void) { FRESULT res; Ctrl_status status; /* Initialize SD/MMC stack. */ sd_mmc_init(); while (true) { printf("init_storage: Please plug an SD/MMC card in slot.\r\n"); /* Wait card present and ready. */ do { status = sd_mmc_test_unit_ready(0); if (CTRL_FAIL == status) { printf("init_storage: SD Card install Failed.\r\n"); printf("init_storage: Please unplug and re-plug the card.\r\n"); while (CTRL_NO_PRESENT != sd_mmc_check(0)) { } } } while (CTRL_GOOD != status); printf("init_storage: Mount SD card...\r\n"); memset(&fatfs, 0, sizeof(FATFS)); res = f_mount(LUN_ID_SD_MMC_0_MEM, &fatfs); if (FR_INVALID_DRIVE == res) { printf("init_storage: SD card Mount failed. res %d\r\n", res); return; } printf("init_storage: SD card Mount OK.\r\n"); add_state(STORAGE_READY); return; } }
//TODO set timeout int fs_mount(void) { Ctrl_status status; FRESULT res; /* Wait card present and ready */ do { status = sd_mmc_test_unit_ready(0); if (CTRL_FAIL == status) { printf("Card install FAIL\n\r"); printf("Please unplug and re-plug the card.\n\r"); //TODO set timeout here while (CTRL_NO_PRESENT != sd_mmc_check(0)); } //TODO set timeout here } while (CTRL_GOOD != status); /* Mount the file sytem */ printf("Mount disk (f_mount)...\r\n"); memset(&fs, 0, sizeof(FATFS)); res = f_mount(LUN_ID_SD_MMC_0_MEM, &fs); if (FR_INVALID_DRIVE == res) { printf("[FAIL] res %d\r\n", res); return res; } #define FS_MOUNTED printf("mounting [OK]\r\n"); return res; }
void memories_initialization(void) { #ifdef CONF_BOARD_SMC_PSRAM psram_init(); #endif #ifdef CONF_BOARD_SRAM sram_init(); #endif #ifdef CONF_BOARD_SDRAMC /* Enable SMC peripheral clock */ pmc_enable_periph_clk(ID_SMC); /* Complete SDRAM configuration */ sdramc_init((sdramc_memory_dev_t *)&SDRAM_MICRON_MT48LC16M16A2, sysclk_get_cpu_hz()); #endif #ifdef CONF_BOARD_AT45DBX at45dbx_init(); if (at45dbx_mem_check() != true) { while (1) { } } #endif #ifdef CONF_BOARD_SD_MMC_HSMCI uint8_t slot = 0; sd_mmc_err_t err; sd_mmc_init(); if (slot == sd_mmc_nb_slot()) { slot = 0; } // Wait for a card and ready do { err = sd_mmc_check(slot); if ((SD_MMC_ERR_NO_CARD != err) && (SD_MMC_INIT_ONGOING != err) && (SD_MMC_OK != err)) { while (SD_MMC_ERR_NO_CARD != sd_mmc_check(slot)) { } } } while (SD_MMC_OK != err); #endif }
void AtmelMemTest(void) { uint8_t slot = 0; sd_mmc_err_t err; REDSTATUS ret; printf("\x0C\n\r-- SD/MMC/SDIO Card Example --\n\r"); printf("-- Compiled: %s %s --\n\r", __DATE__, __TIME__); printf("Please plug an SD, MMC or SDIO card in slot %d.\n\r", slot+1); // Wait for a card and ready do { err = sd_mmc_check(slot); if ((SD_MMC_ERR_NO_CARD != err) && (SD_MMC_INIT_ONGOING != err) && (SD_MMC_OK != err)) { printf("Card install FAILED\n\r"); printf("Please unplug and re-plug the card.\n\r"); while(SD_MMC_ERR_NO_CARD != sd_mmc_check(slot)) { } } } while (SD_MMC_OK != err); // Display basic card information main_display_info_card(slot); ret = RedOsTimestampInit(); if (ret != 0) { printf("Unable to initialize timestamps, err=%d\n\r", (int)ret); return; } /* Test the card */ if (sd_mmc_get_type(slot) & CARD_TYPE_SDIO) { // Test CIA of SDIO card main_test_sdio(slot); } if (sd_mmc_get_type(slot) & (CARD_TYPE_SD | CARD_TYPE_MMC)) { // SD/MMC Card R/W main_test_memory(slot); } (void)RedOsTimestampUninit(); printf("SD/MMC card test finished.\n\r"); }
void datalog_tasks_init(void) { uint8_t slot = 0; sd_mmc_err_t err; sd_mmc_init(); if (slot == sd_mmc_nb_slot()) { slot = 0; } // Wait for a card and ready do { err = sd_mmc_check(slot); if ((SD_MMC_ERR_NO_CARD != err) && (SD_MMC_INIT_ONGOING != err) && (SD_MMC_OK != err)) { while (SD_MMC_ERR_NO_CARD != sd_mmc_check(slot)) { } } } while (SD_MMC_OK != err); }
/** * \brief SD/MMC stack initialization test. * * \param test Current test case. */ static void run_sd_mmc_init_test(const struct test_case *test) { sd_mmc_err_t err; /* Initialize SD MMC stack */ sd_mmc_init(); /* Wait card connection */ do { err = sd_mmc_check(0); } while (SD_MMC_ERR_NO_CARD == err); /* Check if the first state is an initialization */ test_assert_true(test, err == SD_MMC_INIT_ONGOING, "No card initialization phase detected."); /* Check if the second step is an installation success */ test_assert_true(test, sd_mmc_check(0) == SD_MMC_OK, "SD/MMC card initialization failed."); }
/** * \brief SD/MMC/SDIO card read and write test. * * \param test Current test case. */ static void run_sd_mmc_sdio_rw_test(const struct test_case *test) { test_assert_true(test, SD_MMC_OK == sd_mmc_check(0), "SD/MMC card is not initialized OK."); if (sd_mmc_get_type(0) & (CARD_TYPE_SD | CARD_TYPE_MMC)) { run_sd_mmc_rw_test(test); } if (sd_mmc_get_type(0) & CARD_TYPE_SDIO) { run_sdio_rw_test(test); } }
/** * Try to connect to SD/MMC card */ bool media_sd_connect(void) { Ctrl_status status; int i; for (i = 0; i < 5; i ++) { status = sd_mmc_test_unit_ready(0); if (CTRL_GOOD == status) { return true; } if (CTRL_NO_PRESENT == sd_mmc_check(0)) { return false; } } return false; }
void MassStorage::Init() { hsmciPinsinit(); // Initialize SD MMC stack sd_mmc_init(); int sdPresentCount = 0; while ((CTRL_NO_PRESENT == sd_mmc_check(0)) && (sdPresentCount < 5)) { //platform->Message(HOST_MESSAGE, "Please plug in the SD card.\n"); //delay(1000); sdPresentCount++; } if(sdPresentCount >= 5) { platform->Message(HOST_MESSAGE, "Can't find the SD card.\n"); return; } //print card info // SerialUSB.print("sd_mmc_card->capacity: "); // SerialUSB.print(sd_mmc_get_capacity(0)); // SerialUSB.print(" bytes\n"); // SerialUSB.print("sd_mmc_card->clock: "); // SerialUSB.print(sd_mmc_get_bus_clock(0)); // SerialUSB.print(" Hz\n"); // SerialUSB.print("sd_mmc_card->bus_width: "); // SerialUSB.println(sd_mmc_get_bus_width(0)); memset(&fileSystem, 0, sizeof(FATFS)); //f_mount (LUN_ID_SD_MMC_0_MEM, NULL); //int mounted = f_mount(LUN_ID_SD_MMC_0_MEM, &fileSystem); int mounted = f_mount(0, &fileSystem); if (mounted != FR_OK) { platform->Message(HOST_MESSAGE, "Can't mount filesystem 0: code "); snprintf(scratchString, STRING_LENGTH, "%d", mounted); platform->Message(HOST_MESSAGE, scratchString); platform->Message(HOST_MESSAGE, "\n"); } }
/** * \brief waits till sd card is ready * * This function will wait, indefinitely till SD card is ready for access. * */ static void sd_mmc_ready() { Ctrl_status status = CTRL_FAIL; do { status = sd_mmc_test_unit_ready(0); if (CTRL_FAIL == status) { #ifdef __DEBUG_PRINT__ printf("[SD Card install FAILED]\n\r"); printf("Please unplug and re-plug the card!!!\n\r"); #endif while (CTRL_NO_PRESENT != sd_mmc_check(0)) {} } } while (CTRL_GOOD != status); /* Turn on LED if SD card is ready */ port_pin_set_output_level(BOOT_LED, false); #ifdef __DEBUG_PRINT__ printf("SD Card Detection successful...\r\n"); #endif }
/** * \brief Show SD card status on the OLED screen. */ static void display_sd_info(void) { uint8_t card_check; uint8_t sd_card_type; uint8_t sd_card_version; uint32_t sd_card_size; uint8_t size[10]; // Is SD card present? if (gpio_pin_is_low(SD_MMC_0_CD_GPIO) == false) { ssd1306_write_text("Please insert SD card..."); } else { ssd1306_write_text("SD card information:"); sd_mmc_init(); card_check = sd_mmc_check(0); while (card_check != SD_MMC_OK) { card_check = sd_mmc_check(0); delay_ms(1); } if (card_check == SD_MMC_OK) { sd_card_type = sd_mmc_get_type(0); sd_card_version = sd_mmc_get_version(0); sd_card_size = sd_mmc_get_capacity(0); ssd1306_set_page_address(1); ssd1306_set_column_address(0); // Card type switch(sd_card_type) { case CARD_TYPE_SD: ssd1306_write_text("- Type: Normal SD card"); break; case CARD_TYPE_SDIO: ssd1306_write_text("- Type: SDIO card"); break; case CARD_TYPE_HC: ssd1306_write_text("- Type: High Capacity card"); break; case CARD_TYPE_SD_COMBO: ssd1306_write_text("- Type: SDIO/Memory card"); break; default: ssd1306_write_text("- Type: unknown"); } ssd1306_set_page_address(2); ssd1306_set_column_address(0); // SD card version switch(sd_card_version) { case CARD_VER_SD_1_0: ssd1306_write_text("- Version: 1.0x"); break; case CARD_VER_SD_1_10: ssd1306_write_text("- Version: 1.10"); break; case CARD_VER_SD_2_0: ssd1306_write_text("- Version: 2.00"); break; case CARD_VER_SD_3_0: ssd1306_write_text("- Version: 3.0x"); break; default: ssd1306_write_text("- Version: unknown"); } ssd1306_set_page_address(3); ssd1306_set_column_address(0); sprintf(size, "- Total size: %lu KB", sd_card_size); ssd1306_write_text(size); } } }
void ZP_Init(void) { #ifdef DEBUG printf("Setting up system clock...\n"); #endif /* Setup SysTick Timer for 1 msec interrupts */ if (SysTick_Config(sysclk_get_cpu_hz() / 1000)) while (1) {} #ifdef DEBUG printf("ZP Init:\n"); printf("Setting up pins...\n"); #endif #ifdef DEBUG printf("Setting up SD stack...\n"); #endif /* Initialize SD MMC stack */ sd_mmc_init(); uint8_t sd_check = 0; /* Wait card present and ready */ do { #ifdef DEBUG if (sd_check == 1) { printf("Please plug an SD card in slot.\n"); sd_check = 2; } #endif status = sd_mmc_test_unit_ready(0); if (CTRL_FAIL == status) { printf("Card install FAIL\n\r"); printf("Please unplug and re-plug the card.\n\r"); while (CTRL_NO_PRESENT != sd_mmc_check(0)) { } } if (sd_check == 0) sd_check = 1; } while (CTRL_GOOD != status); #ifdef DEBUG printf("SD Card Found\n"); printf("Mounting disk..."); #endif memset(&fs, 0, sizeof(FATFS)); res = f_mount(LUN_ID_SD_MMC_0_MEM, &fs); if (FR_INVALID_DRIVE == res) { printf("[FAIL] res %d\r\n", res); } #ifdef DEBUG printf("Disk mounted\n"); #endif TCHAR root_directory[3] = "0:"; root_directory[0] = '0' + LUN_ID_SD_MMC_0_MEM; file_name[0] = '0' + LUN_ID_SD_MMC_0_MEM; DIR dirs; res = f_opendir(&dirs, root_directory); if(f_opendir(&dir, "0:Scripts") == FR_NO_PATH) { res = f_mkdir("0:Scripts"); printf("Made Scripts folder\n"); } printf("res: %d\n", res); printf("Open Script\n"); //f_open(&f_script, "0:script.bin", FA_OPEN_EXISTING | FA_READ); }
/** * \brief Application entry point. * * \return Unused (ANSI-C compatibility). */ int main(void) { uint8_t slot = 0; sd_mmc_err_t err; const usart_serial_options_t usart_serial_options = { .baudrate = CONF_TEST_BAUDRATE, .charlength = CONF_TEST_CHARLENGTH, .paritytype = CONF_TEST_PARITY, .stopbits = CONF_TEST_STOPBITS, }; irq_initialize_vectors(); cpu_irq_enable(); sysclk_init(); board_init(); stdio_serial_init(CONF_TEST_USART, &usart_serial_options); time_tick_init(); // Initialize SD MMC stack sd_mmc_init(); printf("\x0C\n\r-- SD/MMC/SDIO Card Example --\n\r"); printf("-- Compiled: %s %s --\n\r", __DATE__, __TIME__); while (1) { if (slot == sd_mmc_nb_slot()) { slot = 0; } printf("Please plug an SD, MMC or SDIO card in slot %d.\n\r", slot+1); // Wait for a card and ready do { err = sd_mmc_check(slot); if ((SD_MMC_ERR_NO_CARD != err) && (SD_MMC_INIT_ONGOING != err) && (SD_MMC_OK != err)) { printf("Card install FAILED\n\r"); printf("Please unplug and re-plug the card.\n\r"); while (SD_MMC_ERR_NO_CARD != sd_mmc_check(slot)) { } } } while (SD_MMC_OK != err); // Display basic card information main_display_info_card(slot); /* Test the card */ if (sd_mmc_get_type(slot) & CARD_TYPE_SDIO) { // Test CIA of SDIO card main_test_sdio(slot); } if (sd_mmc_get_type(slot) & (CARD_TYPE_SD | CARD_TYPE_MMC)) { // SD/MMC Card R/W main_test_memory(slot); } printf("Test finished, please unplugged the card.\n\r"); while (SD_MMC_OK == sd_mmc_check(slot)) { } slot++; } }
/** * \brief Show SD card status on the OLED screen. */ static void display_sd_info(void) { FRESULT res; uint8_t card_check; uint8_t sd_card_type; uint32_t sd_card_size; char size[64]; /* Is SD card present? */ if (gpio_pin_is_low(SD_MMC_0_CD_GPIO) == false) { multi_language_show_no_sd_info(); } else { multi_language_show_sd_info(); sd_mmc_init(); card_check = sd_mmc_check(0); while (card_check != SD_MMC_OK) { card_check = sd_mmc_check(0); delay_ms(1); } if (card_check == SD_MMC_OK) { sd_card_type = sd_mmc_get_type(0); sd_card_size = sd_mmc_get_capacity(0); /* Card type */ switch (sd_card_type) { case CARD_TYPE_SD: multi_language_show_normal_card_info(); break; case CARD_TYPE_SDIO: break; case CARD_TYPE_HC: multi_language_show_high_capacity_card_info(); break; case CARD_TYPE_SD_COMBO: break; default: multi_language_show_unknow_card_info(); } multi_language_show_card_size_info(size, sd_card_size); /* Try to mount file system. */ memset(&fs, 0, sizeof(FATFS)); res = f_mount(LUN_ID_SD_MMC_0_MEM, &fs); if (FR_INVALID_DRIVE == res) { multi_language_show_no_fatfs_info(); sd_fs_found = 0; } else { get_num_files_on_sd(); if (sd_num_files == 0) { multi_language_show_no_files_info(); sd_fs_found = 1; } else { multi_language_show_browse_info(); sd_fs_found = 1; } } } } }
/** * \brief Check for valid firmware in SD card. */ static void check_valid_firmware(void) { /* Check if the application bin in SD card */ uint32_t i; uint8_t card_check; FRESULT res; TCHAR path[3]; /* Init the path to "0:" */ path[0] = 0x0030; path[1] = 0x003A; path[2] = 0x0000; /* Is SD card present? */ if (gpio_pin_is_low(SD_MMC_0_CD_GPIO) == false) { return; } sd_mmc_init(); card_check = sd_mmc_check(0); while (card_check != SD_MMC_OK) { card_check = sd_mmc_check(0); delay_ms(1); } /* Try to mount file system. */ memset(&fs, 0, sizeof(FATFS)); res = f_mount(LUN_ID_SD_MMC_0_MEM, &fs); if (FR_INVALID_DRIVE == res) { return; } /* Test if the disk is formatted */ res = f_opendir(&dir, path); if (res != FR_OK) { return; } for (i = 0; i < LANGUAGE_NUMBER; i++) { /* Open the application bin file. */ res = f_open(&file_object, file_name_unicode[i], (FA_OPEN_EXISTING | FA_READ)); if (res != FR_OK) { continue; } /* Close the file*/ res = f_close(&file_object); if (res != FR_OK) { continue; } /* Set the firmware type */ firmware_type |= (0x01 << i); } if ((firmware_type & 0x1F) == 0) { return; } /* Show switch info */ multi_language_show_switch_info(); /* Wait 6 seconds to show above info. */ delay_s(6); /* Set the flag. */ valid_firmware_found = 1; }
/** * \brief Application entry point. * * \return Unused (ANSI-C compatibility). */ int main(void) { char test_file_name[] = "0:sd_mmc_test.txt"; Ctrl_status status; FRESULT res; FATFS fs; FIL file_object; const usart_serial_options_t usart_serial_options = { .baudrate = CONF_TEST_BAUDRATE, .charlength = CONF_TEST_CHARLENGTH, .paritytype = CONF_TEST_PARITY, .stopbits = CONF_TEST_STOPBITS, }; irq_initialize_vectors(); cpu_irq_enable(); sysclk_init(); board_init(); stdio_serial_init(CONF_TEST_USART, &usart_serial_options); /* Initialize SD MMC stack */ sd_mmc_init(); printf("\x0C\n\r-- SD/MMC/SDIO Card Example on FatFs --\n\r"); printf("-- Compiled: %s %s --\n\r", __DATE__, __TIME__); while (1) { printf("Please plug an SD, MMC or SDIO card in slot.\n\r"); /* Wait card present and ready */ do { status = sd_mmc_test_unit_ready(0); if (CTRL_FAIL == status) { printf("Card install FAIL\n\r"); printf("Please unplug and re-plug the card.\n\r"); while (CTRL_NO_PRESENT != sd_mmc_check(0)) { } } } while (CTRL_GOOD != status); printf("Mount disk (f_mount)...\r\n"); memset(&fs, 0, sizeof(FATFS)); res = f_mount(LUN_ID_SD_MMC_0_MEM, &fs); if (FR_INVALID_DRIVE == res) { printf("[FAIL] res %d\r\n", res); goto main_end_of_test; } printf("[OK]\r\n"); printf("Create a file (f_open)...\r\n"); test_file_name[0] = LUN_ID_SD_MMC_0_MEM + '0'; res = f_open(&file_object, (char const *)test_file_name, FA_CREATE_ALWAYS | FA_WRITE); if (res != FR_OK) { printf("[FAIL] res %d\r\n", res); goto main_end_of_test; } printf("[OK]\r\n"); printf("Write to test file (f_puts)...\r\n"); if (0 == f_puts("Test SD/MMC stack\n", &file_object)) { f_close(&file_object); printf("[FAIL]\r\n"); goto main_end_of_test; } printf("[OK]\r\n"); f_close(&file_object); printf("Test successfull.\n\r"); main_end_of_test: printf("Please unplug the card.\n\r"); while (CTRL_NO_PRESENT != sd_mmc_check(0)) { } } }
// Mount the specified SD card, returning true if done, false if needs to be called again. // If an error occurs, return true with the error message in 'reply'. // This may only be called to mount one card at a time. GCodeResult MassStorage::Mount(size_t card, const StringRef& reply, bool reportSuccess) { if (card >= NumSdCards) { reply.copy("SD card number out of range"); return GCodeResult::error; } SdCardInfo& inf = info[card]; MutexLocker lock1(fsMutex); MutexLocker lock2(inf.volMutex); if (!inf.mounting) { if (inf.isMounted) { if (AnyFileOpen(&inf.fileSystem)) { // Don't re-mount the card if any files are open on it reply.copy("SD card has open file(s)"); return GCodeResult::error; } (void)InternalUnmount(card, false); } inf.mountStartTime = millis(); inf.mounting = true; delay(2); } if (inf.cardState == CardDetectState::notPresent) { reply.copy("No SD card present"); inf.mounting = false; return GCodeResult::error; } if (inf.cardState != CardDetectState::present) { return GCodeResult::notFinished; // wait for debounce to finish } const sd_mmc_err_t err = sd_mmc_check(card); if (err != SD_MMC_OK && millis() - inf.mountStartTime < 5000) { delay(2); return GCodeResult::notFinished; } inf.mounting = false; if (err != SD_MMC_OK) { reply.printf("Cannot initialise SD card %u: %s", card, TranslateCardError(err)); return GCodeResult::error; } // Mount the file systems const char path[3] = { (char)('0' + card), ':', 0 }; const FRESULT mounted = f_mount(&inf.fileSystem, path, 1); if (mounted != FR_OK) { reply.printf("Cannot mount SD card %u: code %d", card, mounted); return GCodeResult::error; } inf.isMounted = true; if (reportSuccess) { float capacity = ((float)sd_mmc_get_capacity(card) * 1024) / 1000000; // get capacity and convert from Kib to Mbytes const char* capUnits; if (capacity >= 1000.0) { capacity /= 1000; capUnits = "Gb"; } else { capUnits = "Mb"; } reply.printf("%s card mounted in slot %u, capacity %.2f%s", TranslateCardType(sd_mmc_get_type(card)), card, (double)capacity, capUnits); } return GCodeResult::ok; }