#include <linux/module.h>
#include <linux/bitops.h>
#include <linux/clk.h>
#include <linux/delay.h>
#include <linux/dma-mapping.h>
#include <linux/iopoll.h>
#include <linux/ioport.h>
#include <linux/irq.h>
#include <linux/of.h>
#include <linux/pinctrl/consumer.h>
#include <linux/platform_device.h>
#include <linux/pm.h>
#include <linux/pm_runtime.h>
#include <linux/pm_wakeirq.h>
#include <linux/regulator/consumer.h>
#include <linux/slab.h>
#include <linux/spinlock.h>
#include <linux/interrupt.h>
#include <linux/reset.h>
#include <linux/mmc/card.h>
#include <linux/mmc/core.h>
#include <linux/mmc/host.h>
#include <linux/mmc/mmc.h>
#include <linux/mmc/sd.h>
#include <linux/mmc/sdio.h>
#include <linux/mmc/slot-gpio.h>
#include "cqhci.h"
#define MAX_BD_NUM …
#define MSDC_NR_CLOCKS …
#define MSDC_BUS_1BITS …
#define MSDC_BUS_4BITS …
#define MSDC_BUS_8BITS …
#define MSDC_BURST_64B …
#define MSDC_CFG …
#define MSDC_IOCON …
#define MSDC_PS …
#define MSDC_INT …
#define MSDC_INTEN …
#define MSDC_FIFOCS …
#define SDC_CFG …
#define SDC_CMD …
#define SDC_ARG …
#define SDC_STS …
#define SDC_RESP0 …
#define SDC_RESP1 …
#define SDC_RESP2 …
#define SDC_RESP3 …
#define SDC_BLK_NUM …
#define SDC_ADV_CFG0 …
#define EMMC_IOCON …
#define SDC_ACMD_RESP …
#define DMA_SA_H4BIT …
#define MSDC_DMA_SA …
#define MSDC_DMA_CTRL …
#define MSDC_DMA_CFG …
#define MSDC_PATCH_BIT …
#define MSDC_PATCH_BIT1 …
#define MSDC_PATCH_BIT2 …
#define MSDC_PAD_TUNE …
#define MSDC_PAD_TUNE0 …
#define PAD_DS_TUNE …
#define PAD_CMD_TUNE …
#define EMMC51_CFG0 …
#define EMMC50_CFG0 …
#define EMMC50_CFG1 …
#define EMMC50_CFG3 …
#define SDC_FIFO_CFG …
#define CQHCI_SETTING …
#define EMMC_TOP_CONTROL …
#define EMMC_TOP_CMD …
#define EMMC50_PAD_DS_TUNE …
#define MSDC_CFG_MODE …
#define MSDC_CFG_CKPDN …
#define MSDC_CFG_RST …
#define MSDC_CFG_PIO …
#define MSDC_CFG_CKDRVEN …
#define MSDC_CFG_BV18SDT …
#define MSDC_CFG_BV18PSS …
#define MSDC_CFG_CKSTB …
#define MSDC_CFG_CKDIV …
#define MSDC_CFG_CKMOD …
#define MSDC_CFG_HS400_CK_MODE …
#define MSDC_CFG_HS400_CK_MODE_EXTRA …
#define MSDC_CFG_CKDIV_EXTRA …
#define MSDC_CFG_CKMOD_EXTRA …
#define MSDC_IOCON_SDR104CKS …
#define MSDC_IOCON_RSPL …
#define MSDC_IOCON_DSPL …
#define MSDC_IOCON_DDLSEL …
#define MSDC_IOCON_DDR50CKD …
#define MSDC_IOCON_DSPLSEL …
#define MSDC_IOCON_W_DSPL …
#define MSDC_IOCON_D0SPL …
#define MSDC_IOCON_D1SPL …
#define MSDC_IOCON_D2SPL …
#define MSDC_IOCON_D3SPL …
#define MSDC_IOCON_D4SPL …
#define MSDC_IOCON_D5SPL …
#define MSDC_IOCON_D6SPL …
#define MSDC_IOCON_D7SPL …
#define MSDC_IOCON_RISCSZ …
#define MSDC_PS_CDEN …
#define MSDC_PS_CDSTS …
#define MSDC_PS_CDDEBOUNCE …
#define MSDC_PS_DAT …
#define MSDC_PS_DATA1 …
#define MSDC_PS_CMD …
#define MSDC_PS_WP …
#define MSDC_INT_MMCIRQ …
#define MSDC_INT_CDSC …
#define MSDC_INT_ACMDRDY …
#define MSDC_INT_ACMDTMO …
#define MSDC_INT_ACMDCRCERR …
#define MSDC_INT_DMAQ_EMPTY …
#define MSDC_INT_SDIOIRQ …
#define MSDC_INT_CMDRDY …
#define MSDC_INT_CMDTMO …
#define MSDC_INT_RSPCRCERR …
#define MSDC_INT_CSTA …
#define MSDC_INT_XFER_COMPL …
#define MSDC_INT_DXFER_DONE …
#define MSDC_INT_DATTMO …
#define MSDC_INT_DATCRCERR …
#define MSDC_INT_ACMD19_DONE …
#define MSDC_INT_DMA_BDCSERR …
#define MSDC_INT_DMA_GPDCSERR …
#define MSDC_INT_DMA_PROTECT …
#define MSDC_INT_CMDQ …
#define MSDC_INTEN_MMCIRQ …
#define MSDC_INTEN_CDSC …
#define MSDC_INTEN_ACMDRDY …
#define MSDC_INTEN_ACMDTMO …
#define MSDC_INTEN_ACMDCRCERR …
#define MSDC_INTEN_DMAQ_EMPTY …
#define MSDC_INTEN_SDIOIRQ …
#define MSDC_INTEN_CMDRDY …
#define MSDC_INTEN_CMDTMO …
#define MSDC_INTEN_RSPCRCERR …
#define MSDC_INTEN_CSTA …
#define MSDC_INTEN_XFER_COMPL …
#define MSDC_INTEN_DXFER_DONE …
#define MSDC_INTEN_DATTMO …
#define MSDC_INTEN_DATCRCERR …
#define MSDC_INTEN_ACMD19_DONE …
#define MSDC_INTEN_DMA_BDCSERR …
#define MSDC_INTEN_DMA_GPDCSERR …
#define MSDC_INTEN_DMA_PROTECT …
#define MSDC_FIFOCS_RXCNT …
#define MSDC_FIFOCS_TXCNT …
#define MSDC_FIFOCS_CLR …
#define SDC_CFG_SDIOINTWKUP …
#define SDC_CFG_INSWKUP …
#define SDC_CFG_WRDTOC …
#define SDC_CFG_BUSWIDTH …
#define SDC_CFG_SDIO …
#define SDC_CFG_SDIOIDE …
#define SDC_CFG_INTATGAP …
#define SDC_CFG_DTOC …
#define SDC_STS_SDCBUSY …
#define SDC_STS_CMDBUSY …
#define SDC_STS_SWR_COMPL …
#define SDC_DAT1_IRQ_TRIGGER …
#define SDC_RX_ENHANCE_EN …
#define DMA_ADDR_HIGH_4BIT …
#define MSDC_DMA_CTRL_START …
#define MSDC_DMA_CTRL_STOP …
#define MSDC_DMA_CTRL_RESUME …
#define MSDC_DMA_CTRL_MODE …
#define MSDC_DMA_CTRL_LASTBUF …
#define MSDC_DMA_CTRL_BRUSTSZ …
#define MSDC_DMA_CFG_STS …
#define MSDC_DMA_CFG_DECSEN …
#define MSDC_DMA_CFG_AHBHPROT2 …
#define MSDC_DMA_CFG_ACTIVEEN …
#define MSDC_DMA_CFG_CS12B16B …
#define MSDC_PATCH_BIT_ODDSUPP …
#define MSDC_INT_DAT_LATCH_CK_SEL …
#define MSDC_CKGEN_MSDC_DLY_SEL …
#define MSDC_PATCH_BIT_IODSSEL …
#define MSDC_PATCH_BIT_IOINTSEL …
#define MSDC_PATCH_BIT_BUSYDLY …
#define MSDC_PATCH_BIT_WDOD …
#define MSDC_PATCH_BIT_IDRTSEL …
#define MSDC_PATCH_BIT_CMDFSEL …
#define MSDC_PATCH_BIT_INTDLSEL …
#define MSDC_PATCH_BIT_SPCPUSH …
#define MSDC_PATCH_BIT_DECRCTMO …
#define MSDC_PATCH_BIT1_CMDTA …
#define MSDC_PB1_BUSY_CHECK_SEL …
#define MSDC_PATCH_BIT1_STOP_DLY …
#define MSDC_PATCH_BIT2_CFGRESP …
#define MSDC_PATCH_BIT2_CFGCRCSTS …
#define MSDC_PB2_SUPPORT_64G …
#define MSDC_PB2_RESPWAIT …
#define MSDC_PB2_RESPSTSENSEL …
#define MSDC_PB2_CRCSTSENSEL …
#define MSDC_PAD_TUNE_DATWRDLY …
#define MSDC_PAD_TUNE_DATRRDLY …
#define MSDC_PAD_TUNE_DATRRDLY2 …
#define MSDC_PAD_TUNE_CMDRDLY …
#define MSDC_PAD_TUNE_CMDRDLY2 …
#define MSDC_PAD_TUNE_CMDRRDLY …
#define MSDC_PAD_TUNE_CLKTDLY …
#define MSDC_PAD_TUNE_RXDLYSEL …
#define MSDC_PAD_TUNE_RD_SEL …
#define MSDC_PAD_TUNE_CMD_SEL …
#define MSDC_PAD_TUNE_RD2_SEL …
#define MSDC_PAD_TUNE_CMD2_SEL …
#define PAD_DS_TUNE_DLY_SEL …
#define PAD_DS_TUNE_DLY1 …
#define PAD_DS_TUNE_DLY2 …
#define PAD_DS_TUNE_DLY3 …
#define PAD_CMD_TUNE_RX_DLY3 …
#define CMDQ_RDAT_CNT …
#define EMMC50_CFG_PADCMD_LATCHCK …
#define EMMC50_CFG_CRCSTS_EDGE …
#define EMMC50_CFG_CFCSTS_SEL …
#define EMMC50_CFG_CMD_RESP_SEL …
#define EMMC50_CFG1_DS_CFG …
#define EMMC50_CFG3_OUTS_WR …
#define SDC_FIFO_CFG_WRVALIDSEL …
#define SDC_FIFO_CFG_RDVALIDSEL …
#define CQHCI_RD_CMD_WND_SEL …
#define CQHCI_WR_CMD_WND_SEL …
#define PAD_RXDLY_SEL …
#define DELAY_EN …
#define PAD_DAT_RD_RXDLY2 …
#define PAD_DAT_RD_RXDLY …
#define PAD_DAT_RD_RXDLY2_SEL …
#define PAD_DAT_RD_RXDLY_SEL …
#define DATA_K_VALUE_SEL …
#define SDC_RX_ENH_EN …
#define PAD_CMD_RXDLY2 …
#define PAD_CMD_RXDLY …
#define PAD_CMD_RD_RXDLY2_SEL …
#define PAD_CMD_RD_RXDLY_SEL …
#define PAD_CMD_TX_DLY …
#define PAD_DS_DLY_SEL …
#define PAD_DS_DLY1 …
#define PAD_DS_DLY3 …
#define REQ_CMD_EIO …
#define REQ_CMD_TMO …
#define REQ_DAT_ERR …
#define REQ_STOP_EIO …
#define REQ_STOP_TMO …
#define REQ_CMD_BUSY …
#define MSDC_PREPARE_FLAG …
#define MSDC_ASYNC_FLAG …
#define MSDC_MMAP_FLAG …
#define MTK_MMC_AUTOSUSPEND_DELAY …
#define CMD_TIMEOUT …
#define DAT_TIMEOUT …
#define DEFAULT_DEBOUNCE …
#define TUNING_REG2_FIXED_OFFEST …
#define PAD_DELAY_HALF …
#define PAD_DELAY_FULL …
struct mt_gpdma_desc { … };
struct mt_bdma_desc { … };
struct msdc_dma { … };
struct msdc_save_para { … };
struct mtk_mmc_compatible { … };
struct msdc_tune_para { … };
struct msdc_delay_phase { … };
struct msdc_host { … };
static const struct mtk_mmc_compatible mt2701_compat = …;
static const struct mtk_mmc_compatible mt2712_compat = …;
static const struct mtk_mmc_compatible mt6779_compat = …;
static const struct mtk_mmc_compatible mt6795_compat = …;
static const struct mtk_mmc_compatible mt7620_compat = …;
static const struct mtk_mmc_compatible mt7622_compat = …;
static const struct mtk_mmc_compatible mt7986_compat = …;
static const struct mtk_mmc_compatible mt8135_compat = …;
static const struct mtk_mmc_compatible mt8173_compat = …;
static const struct mtk_mmc_compatible mt8183_compat = …;
static const struct mtk_mmc_compatible mt8516_compat = …;
static const struct of_device_id msdc_of_ids[] = …;
MODULE_DEVICE_TABLE(of, msdc_of_ids);
static void sdr_set_bits(void __iomem *reg, u32 bs)
{ … }
static void sdr_clr_bits(void __iomem *reg, u32 bs)
{ … }
static void sdr_set_field(void __iomem *reg, u32 field, u32 val)
{ … }
static void sdr_get_field(void __iomem *reg, u32 field, u32 *val)
{ … }
static void msdc_reset_hw(struct msdc_host *host)
{ … }
static void msdc_cmd_next(struct msdc_host *host,
struct mmc_request *mrq, struct mmc_command *cmd);
static void __msdc_enable_sdio_irq(struct msdc_host *host, int enb);
static const u32 cmd_ints_mask = …;
static const u32 data_ints_mask = …;
static u8 msdc_dma_calcs(u8 *buf, u32 len)
{ … }
static inline void msdc_dma_setup(struct msdc_host *host, struct msdc_dma *dma,
struct mmc_data *data)
{ … }
static void msdc_prepare_data(struct msdc_host *host, struct mmc_data *data)
{ … }
static void msdc_unprepare_data(struct msdc_host *host, struct mmc_data *data)
{ … }
static u64 msdc_timeout_cal(struct msdc_host *host, u64 ns, u64 clks)
{ … }
static void msdc_set_timeout(struct msdc_host *host, u64 ns, u64 clks)
{ … }
static void msdc_set_busy_timeout(struct msdc_host *host, u64 ns, u64 clks)
{ … }
static void msdc_gate_clock(struct msdc_host *host)
{ … }
static int msdc_ungate_clock(struct msdc_host *host)
{ … }
static void msdc_set_mclk(struct msdc_host *host, unsigned char timing, u32 hz)
{ … }
static inline u32 msdc_cmd_find_resp(struct msdc_host *host,
struct mmc_command *cmd)
{ … }
static inline u32 msdc_cmd_prepare_raw_cmd(struct msdc_host *host,
struct mmc_request *mrq, struct mmc_command *cmd)
{ … }
static void msdc_start_data(struct msdc_host *host, struct mmc_command *cmd,
struct mmc_data *data)
{ … }
static int msdc_auto_cmd_done(struct msdc_host *host, int events,
struct mmc_command *cmd)
{ … }
static void msdc_recheck_sdio_irq(struct msdc_host *host)
{ … }
static void msdc_track_cmd_data(struct msdc_host *host, struct mmc_command *cmd)
{ … }
static void msdc_request_done(struct msdc_host *host, struct mmc_request *mrq)
{ … }
static bool msdc_cmd_done(struct msdc_host *host, int events,
struct mmc_request *mrq, struct mmc_command *cmd)
{ … }
static inline bool msdc_cmd_is_ready(struct msdc_host *host,
struct mmc_request *mrq, struct mmc_command *cmd)
{ … }
static void msdc_start_command(struct msdc_host *host,
struct mmc_request *mrq, struct mmc_command *cmd)
{ … }
static void msdc_cmd_next(struct msdc_host *host,
struct mmc_request *mrq, struct mmc_command *cmd)
{ … }
static void msdc_ops_request(struct mmc_host *mmc, struct mmc_request *mrq)
{ … }
static void msdc_pre_req(struct mmc_host *mmc, struct mmc_request *mrq)
{ … }
static void msdc_post_req(struct mmc_host *mmc, struct mmc_request *mrq,
int err)
{ … }
static void msdc_data_xfer_next(struct msdc_host *host, struct mmc_request *mrq)
{ … }
static void msdc_data_xfer_done(struct msdc_host *host, u32 events,
struct mmc_request *mrq, struct mmc_data *data)
{ … }
static void msdc_set_buswidth(struct msdc_host *host, u32 width)
{ … }
static int msdc_ops_switch_volt(struct mmc_host *mmc, struct mmc_ios *ios)
{ … }
static int msdc_card_busy(struct mmc_host *mmc)
{ … }
static void msdc_request_timeout(struct work_struct *work)
{ … }
static void __msdc_enable_sdio_irq(struct msdc_host *host, int enb)
{ … }
static void msdc_enable_sdio_irq(struct mmc_host *mmc, int enb)
{ … }
static irqreturn_t msdc_cmdq_irq(struct msdc_host *host, u32 intsts)
{ … }
static irqreturn_t msdc_irq(int irq, void *dev_id)
{ … }
static void msdc_init_hw(struct msdc_host *host)
{ … }
static void msdc_deinit_hw(struct msdc_host *host)
{ … }
static void msdc_init_gpd_bd(struct msdc_host *host, struct msdc_dma *dma)
{ … }
static void msdc_ops_set_ios(struct mmc_host *mmc, struct mmc_ios *ios)
{ … }
static u64 test_delay_bit(u64 delay, u32 bit)
{ … }
static int get_delay_len(u64 delay, u32 start_bit)
{ … }
static struct msdc_delay_phase get_best_delay(struct msdc_host *host, u64 delay)
{ … }
static inline void msdc_set_cmd_delay(struct msdc_host *host, u32 value)
{ … }
static inline void msdc_set_data_delay(struct msdc_host *host, u32 value)
{ … }
static int msdc_tune_response(struct mmc_host *mmc, u32 opcode)
{ … }
static int hs400_tune_response(struct mmc_host *mmc, u32 opcode)
{ … }
static int msdc_tune_data(struct mmc_host *mmc, u32 opcode)
{ … }
static int msdc_tune_together(struct mmc_host *mmc, u32 opcode)
{ … }
static int msdc_execute_tuning(struct mmc_host *mmc, u32 opcode)
{ … }
static int msdc_prepare_hs400_tuning(struct mmc_host *mmc, struct mmc_ios *ios)
{ … }
static int msdc_execute_hs400_tuning(struct mmc_host *mmc, struct mmc_card *card)
{ … }
static void msdc_hw_reset(struct mmc_host *mmc)
{ … }
static void msdc_ack_sdio_irq(struct mmc_host *mmc)
{ … }
static int msdc_get_cd(struct mmc_host *mmc)
{ … }
static void msdc_hs400_enhanced_strobe(struct mmc_host *mmc,
struct mmc_ios *ios)
{ … }
static void msdc_cqe_cit_cal(struct msdc_host *host, u64 timer_ns)
{ … }
static void msdc_cqe_enable(struct mmc_host *mmc)
{ … }
static void msdc_cqe_disable(struct mmc_host *mmc, bool recovery)
{ … }
static void msdc_cqe_pre_enable(struct mmc_host *mmc)
{ … }
static void msdc_cqe_post_disable(struct mmc_host *mmc)
{ … }
static const struct mmc_host_ops mt_msdc_ops = …;
static const struct cqhci_host_ops msdc_cmdq_ops = …;
static void msdc_of_property_parse(struct platform_device *pdev,
struct msdc_host *host)
{ … }
static int msdc_of_clock_parse(struct platform_device *pdev,
struct msdc_host *host)
{ … }
static int msdc_drv_probe(struct platform_device *pdev)
{ … }
static void msdc_drv_remove(struct platform_device *pdev)
{ … }
static void msdc_save_reg(struct msdc_host *host)
{ … }
static void msdc_restore_reg(struct msdc_host *host)
{ … }
static int __maybe_unused msdc_runtime_suspend(struct device *dev)
{ … }
static int __maybe_unused msdc_runtime_resume(struct device *dev)
{ … }
static int __maybe_unused msdc_suspend(struct device *dev)
{ … }
static int __maybe_unused msdc_resume(struct device *dev)
{ … }
static const struct dev_pm_ops msdc_dev_pm_ops = …;
static struct platform_driver mt_msdc_driver = …;
module_platform_driver(…) …;
MODULE_LICENSE(…) …;
MODULE_DESCRIPTION(…) …;