From b22da3d8526a935aa31e086e63f60ff3246cb61c Mon Sep 17 00:00:00 2001
From: hc <hc@nodka.com>
Date: Sat, 09 Dec 2023 07:24:11 +0000
Subject: [PATCH] add stmac read mac form eeprom
---
kernel/drivers/mmc/core/sd.c | 169 +++++++++++++++++++++++++++++++++++++++-----------------
1 files changed, 118 insertions(+), 51 deletions(-)
diff --git a/kernel/drivers/mmc/core/sd.c b/kernel/drivers/mmc/core/sd.c
index b85d9fc..e7f2eeb 100644
--- a/kernel/drivers/mmc/core/sd.c
+++ b/kernel/drivers/mmc/core/sd.c
@@ -1,13 +1,10 @@
+// SPDX-License-Identifier: GPL-2.0-only
/*
* linux/drivers/mmc/core/sd.c
*
* Copyright (C) 2003-2004 Russell King, All Rights Reserved.
* SD support Copyright (C) 2004 Ian Molton, All Rights Reserved.
* Copyright (C) 2005-2007 Pierre Ossman, All Rights Reserved.
- *
- * This program is free software; you can redistribute it and/or modify
- * it under the terms of the GNU General Public License version 2 as
- * published by the Free Software Foundation.
*/
#include <linux/err.h>
@@ -20,6 +17,8 @@
#include <linux/mmc/card.h>
#include <linux/mmc/mmc.h>
#include <linux/mmc/sd.h>
+
+#include <trace/hooks/mmc_core.h>
#include "core.h"
#include "card.h"
@@ -215,6 +214,11 @@
/* Check if Physical Layer Spec v3.0 is supported */
scr->sda_spec3 = UNSTUFF_BITS(resp, 47, 1);
+ if (scr->sda_spec3) {
+ scr->sda_spec4 = UNSTUFF_BITS(resp, 42, 1);
+ scr->sda_specx = UNSTUFF_BITS(resp, 38, 4);
+ }
+
if (UNSTUFF_BITS(resp, 55, 1))
card->erased_byte = 0xFF;
else
@@ -240,6 +244,8 @@
{
unsigned int au, es, et, eo;
__be32 *raw_ssr;
+ u32 resp[4] = {};
+ u8 discard_support;
int i;
if (!(card->csd.cmdclass & CCC_APP_SPEC)) {
@@ -284,6 +290,14 @@
mmc_hostname(card->host));
}
}
+
+ /*
+ * starting SD5.1 discard is supported if DISCARD_SUPPORT (b313) is set
+ */
+ resp[3] = card->raw_ssr[6];
+ discard_support = UNSTUFF_BITS(resp, 313 - 288, 1);
+ card->erase_arg = (card->scr.sda_specx && discard_support) ?
+ SD_DISCARD_ARG : SD_ERASE_ARG;
return 0;
}
@@ -370,11 +384,11 @@
if (!status)
return -ENOMEM;
- err = mmc_sd_switch(card, 1, 0, 1, status);
+ err = mmc_sd_switch(card, 1, 0, HIGH_SPEED_BUS_SPEED, status);
if (err)
goto out;
- if ((status[16] & 0xF) != 1) {
+ if ((status[16] & 0xF) != HIGH_SPEED_BUS_SPEED) {
pr_warn("%s: Problem switching card into high-speed mode!\n",
mmc_hostname(card->host));
err = 0;
@@ -450,6 +464,8 @@
SD_MODE_UHS_SDR12)) {
card->sd_bus_speed = UHS_SDR12_BUS_SPEED;
}
+
+ trace_android_vh_sd_update_bus_speed_mode(card);
}
static int sd_set_bus_speed_mode(struct mmc_card *card, u8 *status)
@@ -701,7 +717,36 @@
static DEVICE_ATTR(dsr, S_IRUGO, mmc_dsr_show, NULL);
+MMC_DEV_ATTR(vendor, "0x%04x\n", card->cis.vendor);
+MMC_DEV_ATTR(device, "0x%04x\n", card->cis.device);
+MMC_DEV_ATTR(revision, "%u.%u\n", card->major_rev, card->minor_rev);
+
+#define sdio_info_attr(num) \
+static ssize_t info##num##_show(struct device *dev, struct device_attribute *attr, char *buf) \
+{ \
+ struct mmc_card *card = mmc_dev_to_card(dev); \
+ \
+ if (num > card->num_info) \
+ return -ENODATA; \
+ if (!card->info[num-1][0]) \
+ return 0; \
+ return sprintf(buf, "%s\n", card->info[num-1]); \
+} \
+static DEVICE_ATTR_RO(info##num)
+
+sdio_info_attr(1);
+sdio_info_attr(2);
+sdio_info_attr(3);
+sdio_info_attr(4);
+
static struct attribute *sd_std_attrs[] = {
+ &dev_attr_vendor.attr,
+ &dev_attr_device.attr,
+ &dev_attr_revision.attr,
+ &dev_attr_info1.attr,
+ &dev_attr_info2.attr,
+ &dev_attr_info3.attr,
+ &dev_attr_info4.attr,
&dev_attr_cid.attr,
&dev_attr_csd.attr,
&dev_attr_scr.attr,
@@ -720,7 +765,32 @@
&dev_attr_dsr.attr,
NULL,
};
-ATTRIBUTE_GROUPS(sd_std);
+
+static umode_t sd_std_is_visible(struct kobject *kobj, struct attribute *attr,
+ int index)
+{
+ struct device *dev = kobj_to_dev(kobj);
+ struct mmc_card *card = mmc_dev_to_card(dev);
+
+ /* CIS vendor and device ids, revision and info string are available only for Combo cards */
+ if ((attr == &dev_attr_vendor.attr ||
+ attr == &dev_attr_device.attr ||
+ attr == &dev_attr_revision.attr ||
+ attr == &dev_attr_info1.attr ||
+ attr == &dev_attr_info2.attr ||
+ attr == &dev_attr_info3.attr ||
+ attr == &dev_attr_info4.attr
+ ) && card->type != MMC_TYPE_SD_COMBO)
+ return 0;
+
+ return attr->mode;
+}
+
+static const struct attribute_group sd_std_group = {
+ .attrs = sd_std_attrs,
+ .is_visible = sd_std_is_visible,
+};
+__ATTRIBUTE_GROUPS(sd_std);
struct device_type sd_type = {
.groups = sd_std_groups,
@@ -787,7 +857,8 @@
* the CCS bit is set as well. We deliberately deviate from the spec in
* regards to this, which allows UHS-I to be supported for SDSC cards.
*/
- if (!mmc_host_is_spi(host) && rocr && (*rocr & 0x01000000)) {
+ if (!mmc_host_is_spi(host) && (ocr & SD_OCR_S18R) &&
+ rocr && (*rocr & SD_ROCR_S18A)) {
err = mmc_set_uhs_voltage(host, pocr);
if (err == -EAGAIN) {
retries--;
@@ -866,14 +937,15 @@
/* Erase init depends on CSD and SSR */
mmc_init_erase(card);
-
- /*
- * Fetch switch information from card.
- */
- err = mmc_read_switch(card);
- if (err)
- return err;
}
+
+ /*
+ * Fetch switch information from card. Note, sd3_bus_mode can change if
+ * voltage switch outcome changes, so do this always.
+ */
+ err = mmc_read_switch(card);
+ if (err)
+ return err;
/*
* For SPI, enable CRC as appropriate.
@@ -952,8 +1024,11 @@
return err;
if (oldcard) {
- if (memcmp(cid, oldcard->raw_cid, sizeof(cid)) != 0)
+ if (memcmp(cid, oldcard->raw_cid, sizeof(cid)) != 0) {
+ pr_debug("%s: Perhaps the card was replaced\n",
+ mmc_hostname(host));
return -ENOENT;
+ }
card = oldcard;
} else {
@@ -1020,26 +1095,15 @@
if (!v18_fixup_failed && !mmc_host_is_spi(host) && mmc_host_uhs(host) &&
mmc_sd_card_using_v18(card) &&
host->ios.signal_voltage != MMC_SIGNAL_VOLTAGE_180) {
- /*
- * Re-read switch information in case it has changed since
- * oldcard was initialized.
- */
- if (oldcard) {
- err = mmc_read_switch(card);
- if (err)
- goto free_card;
+ if (mmc_host_set_uhs_voltage(host) ||
+ mmc_sd_init_uhs_card(card)) {
+ v18_fixup_failed = true;
+ mmc_power_cycle(host, ocr);
+ if (!oldcard)
+ mmc_remove_card(card);
+ goto retry;
}
- if (mmc_sd_card_using_v18(card)) {
- if (mmc_host_set_uhs_voltage(host) ||
- mmc_sd_init_uhs_card(card)) {
- v18_fixup_failed = true;
- mmc_power_cycle(host, ocr);
- if (!oldcard)
- mmc_remove_card(card);
- goto retry;
- }
- goto done;
- }
+ goto cont;
}
/* Initialization sequence for UHS-I cards */
@@ -1074,6 +1138,16 @@
mmc_set_bus_width(host, MMC_BUS_WIDTH_4);
}
}
+cont:
+ if (host->cqe_ops && !host->cqe_enabled) {
+ err = host->cqe_ops->cqe_enable(host, card);
+ if (!err) {
+ host->cqe_enabled = true;
+ host->hsq_enabled = true;
+ pr_info("%s: Host Software Queue enabled\n",
+ mmc_hostname(host));
+ }
+ }
if (host->caps2 & MMC_CAP2_AVOID_3_3V &&
host->ios.signal_voltage == MMC_SIGNAL_VOLTAGE_330) {
@@ -1082,7 +1156,7 @@
err = -EINVAL;
goto free_card;
}
-done:
+
host->card = card;
return 0;
@@ -1162,8 +1236,8 @@
{
int err = 0;
- BUG_ON(!host);
- BUG_ON(!host->card);
+ if (WARN_ON(!host) || WARN_ON(!host->card))
+ return 0;
mmc_claim_host(host);
@@ -1178,19 +1252,10 @@
mmc_card_set_suspended(host->card);
}
- /*
- * mmc_sd_shutdown is used for SD card, so what we need
- * is to make sure we set signal voltage to initial state
- * if it's used as main disk. RESTRICT_CARD_TYPE_MMC is
- * combined into host->restrict_caps via DT for SD cards
- * running system image.
- */
- if (host->restrict_caps & RESTRICT_CARD_TYPE_EMMC) {
- host->ios.signal_voltage = MMC_SIGNAL_VOLTAGE_330;
- host->ios.vdd = fls(host->ocr_avail) - 1;
- mmc_regulator_set_vqmmc(host, &host->ios);
- pr_info("Set signal voltage to initial state\n");
- }
+ host->ios.signal_voltage = MMC_SIGNAL_VOLTAGE_330;
+ host->ios.vdd = fls(host->ocr_avail) - 1;
+ mmc_regulator_set_vqmmc(host, &host->ios);
+ pr_info("Set signal voltage to initial state\n");
out:
mmc_release_host(host);
@@ -1378,5 +1443,7 @@
pr_err("%s: error %d whilst initialising SD card\n",
mmc_hostname(host), err);
+ trace_android_vh_mmc_attach_sd(host, ocr, err);
+
return err;
}
--
Gitblit v1.6.2