diff -drupN a/drivers/mmc/host/sunxi-smhc.h b/drivers/mmc/host/sunxi-smhc.h --- a/drivers/mmc/host/sunxi-smhc.h 1970-01-01 03:00:00.000000000 +0300 +++ b/drivers/mmc/host/sunxi-smhc.h 2022-06-12 05:28:14.000000000 +0300 @@ -0,0 +1,362 @@ +/* +* Sunxi SD/MMC host driver +* +* Copyright (C) 2015 AllWinnertech Ltd. +* Author: lixiang +* +* 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. +* +* This program is distributed "as is" WITHOUT ANY WARRANTY of any +* kind, whether express or implied; without even the implied warranty +* of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +* GNU General Public License for more details. +*/ + + +#include +#include + +#include +#include +#include +#include +#include +#include +#include + +#include +#include +#include + +#include +#include +#include +#include +#include +#include +#include + +#ifndef __SUNXI_MMC_H__ +#define __SUNXI_MMC_H__ + +#define DRIVER_NAME "sunxi-smhc" +#define DRIVER_RIVISION "v0.6 2016-4-29 16:53" +#define DRIVER_VERSION "SD/MMC/SDIO Host Controller Driver(" DRIVER_RIVISION ")" + +#if defined CONFIG_FPGA_V4_PLATFORM || defined CONFIG_FPGA_V7_PLATFORM +#define MMC_FPGA +#endif + + +#define SMHC_DEVICE_ID (2) /*number of id in multi device*/ +/*max blk count and size is limited by the SMHC_BLK_CFG register's max value*/ +#define MAX_BLK_COUNT (0xFFFF) +#define MAX_BLK_SIZE (0x800) +/*#define MAX_DES_SIZE PAGE_SIZE*/ +#define SUNXI_REQ_PAGE_SIZE (PAGE_SIZE*4) + +/*---------------------------------------------*/ +/* registers define */ +/*---------------------------------------------*/ +#define SMHC_CMD_ARG2 (0x00) +#define SMHC_BLK_CFG (0x04) +#define SMHC_CMD_ARG1 (0x08) +#define SMHC_CMD (0x0C) +#define SMHC_RESP0 (0x10) +#define SMHC_RESP1 (0x14) +#define SMHC_RESP2 (0x18) +#define SMHC_RESP3 (0x1C) +#define SMHC_BUFF (0x20) +#define SMHC_STA (0x24) +#define SMHC_CTRL1 (0x28) +#define SMHC_RST_CLK_CTRL (0x2C) +#define SMHC_INT_STA (0x30) +#define SMHC_INT_STA_EN (0x34) +#define SMHC_INT_SIG_EN (0x38) +#define SMHC_ACMD_ERR_CTRL2 (0x3C) +#define SMHC_SET_ERR (0x50) +#define SMHC_ADMA_ERR (0x54) +#define SMHC_ADMA_ADDR (0x58) + +#define SMHC_CTRL3 (0x200) +#define SMHC_CMD_ATTR (0x204) +#define SMHC_TO_CTRL2 (0x208) +#define SMHC_ATC (0x210) +#define SMHC_RTC (0x214) +#define SMHC_DITC0 (0x218) +#define SMHC_DITC1 (0x21C) +#define SMHC_TP0 (0x220) +#define SMHC_TP1 (0x224) + +#define SMHC_CRC_STA (0x240) +#define SMHC_TBC0 (0x244) +#define SMHC_TBC1 (0x248) +#define SMHC_BL (0x24C) +#define SMHC_CEDBN (0x250) +/*----------------------------------------*/ + +#define smhc_readl(host, reg) \ + __raw_readl((host)->reg_base + reg) +#define smhc_writel(host, reg, value) \ + __raw_writel((value), (host)->reg_base + reg) +#define smhc_readw(host, reg) \ + __raw_readw((host)->reg_base + reg) +#define smhc_writew(host, reg, value) \ + __raw_writew((value), (host)->reg_base + reg) +#define smhc_clr_bit(host, reg, bitmap) \ + do { \ + u32 tmp = smhc_readl(host, reg); \ + tmp &= ~(bitmap); \ + smhc_writel(host, reg, tmp); \ + } while (0) + +#define smhc_set_bit(host, reg, bitmap) \ + do { \ + u32 tmp = smhc_readl(host, reg); \ + tmp |= (bitmap); \ + smhc_writel(host, reg, tmp); \ + } while (0) + + /* control register bit field */ + /*0x2c */ +#define ResetAll (0x1U<<24) +#define ResetCmd (0x1U<<25) +#define ResetDat (0x1U<<26) +#define SdclkEn (0x1U<<2) + + /*0x200 */ +#define CPUAcessBuffEn (0x1U<<31) +#define StopReadClkAtBlkGap (0x1U<<8) +#define SWDebounceMode (0x1U<<5) +#define DebounceEnb (0x1U<<4) +#define CdDat3En (0x1U<<3) +#define SdclkIdleCtrl (0x1U<<2) + + /* Struct for SMC Commands */ + /*0x18 */ +#define CMDType (0x3U<<22) +#define DataExp (0x1U<<21) +#define CheckRspIdx (0x1U<<20) +#define CheckRspCRC (0x1U<<19) +#define NoRsp (0x0U<<16) +#define Rsp136 (0x1U<<16) +#define Rsp48 (0x2U<<16) +#define Rsp48b (0x3U<<16) +#define SingleBlkTrans (0x0U<<5) +#define MultiBlkTrans (0x1U<<5) +#define Read (0x1U<<4) +#define Write (0x0U<<4) +#define AutoCmd12 (0x1U<<2) +#define AutoCmd23 (0x2U<<2) +#define BlkCntEn (0x1U<<1) +#define DMAEn (0x1U<<0) + + /*0x204 */ +#define SendInitSeq (0x1U<<4) +#define DisableBoot (0x1U<<3) +#define BootACKExp (0x1U<<2) +#define AltBootMode (0x2U<<0) +#define MandBootMode (0x1U<<0) + + /*0x03C */ +#define Switch3v3To1v8 (0x1U<<19) +#define DdrType (0x7<<16) +#define DDR_SHIFT (16) + + /*0x24 */ +#define CmdLineSta (0x1U<<24) +#define Dat3LineSta (0x1U<<23) +#define Dat2LineSta (0x1U<<22) +#define Dat1LineSta (0x1U<<21) +#define Dat0LineSta (0x1U<<20) +#define WpPinSta (0x1U<<19) +#define CdPinInvSta (0x1U<<18) +#define CardStable (0x1U<<17) +#define CardInsert (0x1U<<16) +#define BuffRDEn (0x1U<<11) +#define BuffWREn (0x1U<<10) +#define RDTransActive (0x1U<<9) +#define WRTransActive (0x1U<<8) +#define DatLineActive (0x1U<<2) +#define CmdInhibitDat (0x1U<<1) +#define CmdInhibitCmd (0x1U<<0) + +#define BootDataStart (0x1U<<29) +#define BootAckRcv (0x1U<<28) +#define DSFOInt (0x1U<<30) +#define DmaErrInt (0x1U<<25) +#define AcmdErrInt (0x1U<<24) +#define DatEndBitErrInt (0x1U<<22) +#define DatCRCErrInt (0x1U<<21) +#define DatTimeoutErrInt (0x1U<<20) +#define CmdIdxErrInt (0x1U<<19) +#define CmdEndBitErrInt (0x1U<<18) +#define CmdCRCErrInt (0x1U<<17) +#define CmdTimeoutErrInt (0x1U<<16) +#define ErrInt (0x1U<<15) +#define CardInt (0x1U<<8) +#define CardRemoveInt (0x1U<<7) +#define CardInsertInt (0x1U<<6) +#define BuffRDRdyInt (0x1U<<5) +#define BuffWRRdyInt (0x1U<<4) +#define DmaInt (0x1U<<3) + /*#define BlkGapEvtInt (0x1U<<2)*/ +#define TransOverInt (0x1U<<1) +#define CmdOverInt (0x1U<<0) +#define TxDatIntBit (DmaInt | TransOverInt | DmaErrInt | ErrInt) +#define RxDatIntBit (DmaInt | TransOverInt | DmaErrInt | ErrInt) +#define DmaIntBit (DmaInt | DmaErrInt) +#define ErrIntBit (0x437F0000) /*(0x1ff<<16)*/ +#define DoneIntBit (TransOverInt|CmdOverInt) + + /*0x28 SMHC_CTRL1 bit field*/ +#define Dma32BitSel (0x3<<3) +#define DmaSel (0x3<<3) +#define BusWidth (0x1<<1) +#define ExtBusWidth (0x1<<5) + + /*0x3C Auto CMD Error Status */ +#define NoAcmd12 (0x1U<<7) +#define AcmdIdxErr (0x1U<<4) +#define AcmdEndBitErr (0x1U<<3) +#define AcmdCRCErr (0x1U<<2) +#define AcmdTimeoutErr (0x1U<<1) +#define NotIssueAcmd (0x0<<0) + +enum { + ACT_NOP = 0, + ACT_RSV, + ACT_TRANS, + ACT_LINK, +}; + +enum { + MAN_BOOT_MD = 0, + ALT_BOOT_MD, +}; + +struct sdhc_idma_des { +/*=1: indicates this line of descriptor is effective. + *=0: generate ADMA Error interrupt and stop ADMA to prevent runaway. + */ + u32 valid:1, +/*=1: indicates end of descriptor. + *The Transfer Complete Interrupt is generated + *when the operation of the descriptor line is completed. + */ + end:1, +/* + *=1: generates DMA Interrupt + *when the operation of the descriptor line is completed. + */ + int_en:1, + : 1, +/*00b: Nop, No Operation, Do not execute current line and go to next line.*/ +act:2, +/*01b: rsv, reserved, (Same as Nop. Do not execute current line + *and go to next line.) + */ +/*10b: Tran, transfer data, Transfer data of one descriptor + *line Transfer data of one descriptor line + */ +/*11b: Link, Link Descriptor, Link to another descriptor*/ + : 10, + length:16; + u32 addr; +}; + +struct sunxi_mmc_ctrl_regs { + u32 rst_clk_ctrl; + u32 int_sta_en; + u32 to; + u32 ctrl3; + u32 int_sig_en; + u32 ctrl1; + u32 acmd_err_ctrl2; + u32 atc; +}; + +struct sunxi_mmc_host { + struct mmc_host *mmc; + struct reset_control *reset; + + /* IO mapping base */ + void __iomem *reg_base; + + /* clock management */ + struct clk *clk_ahb; + struct clk *clk_mmc; + struct clk *clk_rst; + + int (*sunxi_mmc_clk_set_rate)(struct sunxi_mmc_host *host, + struct mmc_ios *ios); + + /* irq */ + spinlock_t lock; + int irq; + u32 int_sum; + u32 sdio_imask; + + /* dma */ + u32 idma_des_size_bits; + dma_addr_t sg_dma; + void *sg_cpu; + bool wait_dma; + u32 dma_tl; + u64 dma_mask; + + void (*sunxi_mmc_thld_ctl)(struct sunxi_mmc_host *host, + struct mmc_ios *ios, + struct mmc_data *data); + + struct mmc_request *mrq; + struct mmc_request *mrq_busy; + struct mmc_request *manual_stop_mrq; + int ferror; + + u32 power_on; + + /* pinctrl handles */ + struct pinctrl *pinctrl; + struct pinctrl_state *pins_default; + struct pinctrl_state *pins_sleep; + + /*sys node */ + struct device_attribute maual_insert; + struct device_attribute *dump_register; + struct device_attribute dump_clk_dly; + void (*sunxi_mmc_dump_dly_table)(struct sunxi_mmc_host *host); + + /* backup register structrue */ + struct sunxi_mmc_ctrl_regs bak_regs; + void (*sunxi_mmc_save_spec_reg)(struct sunxi_mmc_host *host); + void (*sunxi_mmc_restore_spec_reg)(struct sunxi_mmc_host *host); + + void (*sunxi_mmc_set_acmda)(struct sunxi_mmc_host *host); + + void (*sunxi_mmc_shutdown)(struct platform_device *pdev); + + /*really controller id,no logic id */ + int phy_index; + + u32 dat3_imask; + + /*no wait busy if wrtie end, only for customer need */ +#define NO_MANUAL_WAIT_BUSY_WRITE_END 0x1 +#define NO_REINIT_SHUTDOWN 0x2 +#define CARD_PWR_GPIO_HIGH_ACTIVE 0x4 + /*control specal function control,for customer need */ + u32 ctl_spec_cap; + + int card_pwr_gpio; + + void *version_priv_dat; +}; + +/*use to check ddr mode,not include hs400*/ +#define sunxi_mmc_ddr_timing(it) \ + (((it) == MMC_TIMING_UHS_DDR50) || ((it) == MMC_TIMING_MMC_DDR52)) + +#endif