From 1e9473f97e19b71c6783a0131eb071e2988ae9ee Mon Sep 17 00:00:00 2001 From: PulkoMandy Date: Tue, 5 May 2026 21:15:38 +0200 Subject: [PATCH] mmc: handle "high capacity' (>2GB) devices similarly to SDHC A similar change was made to address sectors instead of bytes. The detection method is different in the initialization sequence. Change-Id: I38af6e21b720d4437594431964a5244fb0d80848 Reviewed-on: https://review.haiku-os.org/c/haiku/+/10933 Reviewed-by: Adrien Destugues Tested-by: Commit checker robot --- headers/private/drivers/mmc.h | 1 + .../kernel/bus_managers/mmc/mmc_bus.cpp | 20 +++++++++---------- .../kernel/drivers/disk/mmc/mmc_disk.cpp | 6 ++++-- 3 files changed, 15 insertions(+), 12 deletions(-) diff --git a/headers/private/drivers/mmc.h b/headers/private/drivers/mmc.h index 9ea562af86..1cd014e80c 100644 --- a/headers/private/drivers/mmc.h +++ b/headers/private/drivers/mmc.h @@ -20,6 +20,7 @@ struct IOOperation; typedef enum card_type { CARD_TYPE_UNKNOWN, CARD_TYPE_MMC, + CARD_TYPE_MMC_EXTENDED_CAPACITY, CARD_TYPE_SD, CARD_TYPE_SDHC, CARD_TYPE_UHS1, diff --git a/src/add-ons/kernel/bus_managers/mmc/mmc_bus.cpp b/src/add-ons/kernel/bus_managers/mmc/mmc_bus.cpp index 287931040b..116cb64f1d 100644 --- a/src/add-ons/kernel/bus_managers/mmc/mmc_bus.cpp +++ b/src/add-ons/kernel/bus_managers/mmc/mmc_bus.cpp @@ -224,27 +224,27 @@ MMCBus::_WorkerThread(void* cookie) TRACE("Card does not implement CMD8, may be a V1 SD or MMC card\n"); // Do not check for SDHC support in this case hcs = 0; - uint32_t mmcOcr; TRACE("Trying MMC CMD1 initialization...\n"); do { - status = bus->ExecuteCommand(0, MMC_SEND_OP_COND, 0xFF8000, &mmcOcr); + status = bus->ExecuteCommand(0, MMC_SEND_OP_COND, 0xFF8000, &ocr); // full voltage window, byte addressable, should look into this. if (status != B_OK) { TRACE("MMC CMD1 failed\n"); break; } - if ((mmcOcr & (1 << 31)) == 0) { + if ((ocr & (1 << 31)) == 0) { TRACE("MMC card is busy\n"); snooze(100000); } - } while ((mmcOcr & (1 << 31)) == 0); + } while ((ocr & (1 << 31)) == 0); - if (status == B_OK && (mmcOcr & (1 << 31)) != 0) { + if (status == B_OK && (ocr & (1 << 31)) != 0) { TRACE("Detected MMC card after CMD1\n"); - cardType = CARD_TYPE_MMC; - // Reuse the probed OCR value for logging and later handling - ocr = mmcOcr; + if ((ocr & (1 << 30)) != 0) + cardType = CARD_TYPE_MMC_EXTENDED_CAPACITY; + else + cardType = CARD_TYPE_MMC; } } else if (response != probe) { ERROR("Card does not support voltage range (expected %x, " @@ -257,7 +257,7 @@ MMCBus::_WorkerThread(void* cookie) // Probe OCR, waiting for card to become ready // We keep repeating ACMD41 until the card replies that it is // initialized. For MMC we already probed using CMD1 above. - if (cardType != CARD_TYPE_MMC) { + if ((cardType != CARD_TYPE_MMC) && (cardType != CARD_TYPE_MMC_EXTENDED_CAPACITY)) { do { uint32_t cardStatus; while (bus->ExecuteCommand(0, SD_APP_CMD, 0, &cardStatus) == B_BUSY) { @@ -314,7 +314,7 @@ MMCBus::_WorkerThread(void* cookie) bool cardFound = false; // This being an if statement as opposed to a while statement restricts // it to one device per bus. - if (cardType == CARD_TYPE_MMC) { + if ((cardType == CARD_TYPE_MMC) || (cardType == CARD_TYPE_MMC_EXTENDED_CAPACITY)) { if (bus->ExecuteCommand(0, ALL_SEND_CID, 0, cid) == B_OK) { // We currently support only a single card, so use a fixed RCA. rca = 1; diff --git a/src/add-ons/kernel/drivers/disk/mmc/mmc_disk.cpp b/src/add-ons/kernel/drivers/disk/mmc/mmc_disk.cpp index e4094ced94..c69de71010 100644 --- a/src/add-ons/kernel/drivers/disk/mmc/mmc_disk.cpp +++ b/src/add-ons/kernel/drivers/disk/mmc/mmc_disk.cpp @@ -101,7 +101,10 @@ mmc_disk_supports_device(device_node* parent) TRACE("SD card found, parent: %p\n", parent); else if (deviceType == CARD_TYPE_SDHC) TRACE("SDHC card found, parent: %p\n", parent); - else + else if (deviceType == CARD_TYPE_SDIO) { + // Ignore silently, since it is not mass storage and should be handled by other drivers + return 0.0; + } else return 0.0; return 0.8; @@ -237,7 +240,6 @@ mmc_disk_init_driver(device_node* node, void** cookie) // SD and MMC cards use byte offsets for IO commands, later ones (SDHC, // SDXC, ...) use sectors. - // TODO eMMC uses sectors as well if defined in the OCR register bits 30:29 if (deviceType == CARD_TYPE_SD || deviceType == CARD_TYPE_MMC) info->flags = 0; else