mmci.h 5.7 KB
Newer Older
L
Linus Torvalds 已提交
1
/*
P
Pierre Ossman 已提交
2
 *  linux/drivers/mmc/host/mmci.h - ARM PrimeCell MMCI PL180/1 driver
L
Linus Torvalds 已提交
3 4 5 6 7 8 9 10 11 12 13
 *
 *  Copyright (C) 2003 Deep Blue Solutions, Ltd, 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.
 */
#define MMCIPOWER		0x000
#define MCI_PWR_OFF		0x00
#define MCI_PWR_UP		0x02
#define MCI_PWR_ON		0x03
14 15 16 17
#define MCI_DATA2DIREN		(1 << 2)
#define MCI_CMDDIREN		(1 << 3)
#define MCI_DATA0DIREN		(1 << 4)
#define MCI_DATA31DIREN		(1 << 5)
L
Linus Torvalds 已提交
18 19
#define MCI_OD			(1 << 6)
#define MCI_ROD			(1 << 7)
20 21 22
/* The ST Micro version does not have ROD */
#define MCI_FBCLKEN		(1 << 7)
#define MCI_DATA74DIREN		(1 << 8)
L
Linus Torvalds 已提交
23 24 25 26 27

#define MMCICLOCK		0x004
#define MCI_CLK_ENABLE		(1 << 8)
#define MCI_CLK_PWRSAVE		(1 << 9)
#define MCI_CLK_BYPASS		(1 << 10)
28 29 30
#define MCI_4BIT_BUS		(1 << 11)
/* 8bit wide buses supported in ST Micro versions */
#define MCI_ST_8BIT_BUS		(1 << 12)
31
/* HW flow control on the ST Micro version */
32
#define MCI_ST_FCEN		(1 << 13)
L
Linus Torvalds 已提交
33 34 35 36 37 38 39 40

#define MMCIARGUMENT		0x008
#define MMCICOMMAND		0x00c
#define MCI_CPSM_RESPONSE	(1 << 6)
#define MCI_CPSM_LONGRSP	(1 << 7)
#define MCI_CPSM_INTERRUPT	(1 << 8)
#define MCI_CPSM_PENDING	(1 << 9)
#define MCI_CPSM_ENABLE		(1 << 10)
41 42 43 44
#define MCI_SDIO_SUSP		(1 << 11)
#define MCI_ENCMD_COMPL		(1 << 12)
#define MCI_NIEN		(1 << 13)
#define MCI_CE_ATACMD		(1 << 14)
L
Linus Torvalds 已提交
45 46 47 48 49 50 51 52 53 54 55 56 57

#define MMCIRESPCMD		0x010
#define MMCIRESPONSE0		0x014
#define MMCIRESPONSE1		0x018
#define MMCIRESPONSE2		0x01c
#define MMCIRESPONSE3		0x020
#define MMCIDATATIMER		0x024
#define MMCIDATALENGTH		0x028
#define MMCIDATACTRL		0x02c
#define MCI_DPSM_ENABLE		(1 << 0)
#define MCI_DPSM_DIRECTION	(1 << 1)
#define MCI_DPSM_MODE		(1 << 2)
#define MCI_DPSM_DMAENABLE	(1 << 3)
58 59 60 61 62
#define MCI_DPSM_BLOCKSIZE	(1 << 4)
#define MCI_DPSM_RWSTART	(1 << 8)
#define MCI_DPSM_RWSTOP		(1 << 9)
#define MCI_DPSM_RWMOD		(1 << 10)
#define MCI_DPSM_SDIOEN		(1 << 11)
L
Linus Torvalds 已提交
63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86

#define MMCIDATACNT		0x030
#define MMCISTATUS		0x034
#define MCI_CMDCRCFAIL		(1 << 0)
#define MCI_DATACRCFAIL		(1 << 1)
#define MCI_CMDTIMEOUT		(1 << 2)
#define MCI_DATATIMEOUT		(1 << 3)
#define MCI_TXUNDERRUN		(1 << 4)
#define MCI_RXOVERRUN		(1 << 5)
#define MCI_CMDRESPEND		(1 << 6)
#define MCI_CMDSENT		(1 << 7)
#define MCI_DATAEND		(1 << 8)
#define MCI_DATABLOCKEND	(1 << 10)
#define MCI_CMDACTIVE		(1 << 11)
#define MCI_TXACTIVE		(1 << 12)
#define MCI_RXACTIVE		(1 << 13)
#define MCI_TXFIFOHALFEMPTY	(1 << 14)
#define MCI_RXFIFOHALFFULL	(1 << 15)
#define MCI_TXFIFOFULL		(1 << 16)
#define MCI_RXFIFOFULL		(1 << 17)
#define MCI_TXFIFOEMPTY		(1 << 18)
#define MCI_RXFIFOEMPTY		(1 << 19)
#define MCI_TXDATAAVLBL		(1 << 20)
#define MCI_RXDATAAVLBL		(1 << 21)
87 88
#define MCI_SDIOIT		(1 << 22)
#define MCI_CEATAEND		(1 << 23)
L
Linus Torvalds 已提交
89 90 91 92 93 94 95 96 97 98 99 100

#define MMCICLEAR		0x038
#define MCI_CMDCRCFAILCLR	(1 << 0)
#define MCI_DATACRCFAILCLR	(1 << 1)
#define MCI_CMDTIMEOUTCLR	(1 << 2)
#define MCI_DATATIMEOUTCLR	(1 << 3)
#define MCI_TXUNDERRUNCLR	(1 << 4)
#define MCI_RXOVERRUNCLR	(1 << 5)
#define MCI_CMDRESPENDCLR	(1 << 6)
#define MCI_CMDSENTCLR		(1 << 7)
#define MCI_DATAENDCLR		(1 << 8)
#define MCI_DATABLOCKENDCLR	(1 << 10)
101 102
#define MCI_SDIOITC		(1 << 22)
#define MCI_CEATAENDC		(1 << 23)
L
Linus Torvalds 已提交
103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125

#define MMCIMASK0		0x03c
#define MCI_CMDCRCFAILMASK	(1 << 0)
#define MCI_DATACRCFAILMASK	(1 << 1)
#define MCI_CMDTIMEOUTMASK	(1 << 2)
#define MCI_DATATIMEOUTMASK	(1 << 3)
#define MCI_TXUNDERRUNMASK	(1 << 4)
#define MCI_RXOVERRUNMASK	(1 << 5)
#define MCI_CMDRESPENDMASK	(1 << 6)
#define MCI_CMDSENTMASK		(1 << 7)
#define MCI_DATAENDMASK		(1 << 8)
#define MCI_DATABLOCKENDMASK	(1 << 10)
#define MCI_CMDACTIVEMASK	(1 << 11)
#define MCI_TXACTIVEMASK	(1 << 12)
#define MCI_RXACTIVEMASK	(1 << 13)
#define MCI_TXFIFOHALFEMPTYMASK	(1 << 14)
#define MCI_RXFIFOHALFFULLMASK	(1 << 15)
#define MCI_TXFIFOFULLMASK	(1 << 16)
#define MCI_RXFIFOFULLMASK	(1 << 17)
#define MCI_TXFIFOEMPTYMASK	(1 << 18)
#define MCI_RXFIFOEMPTYMASK	(1 << 19)
#define MCI_TXDATAAVLBLMASK	(1 << 20)
#define MCI_RXDATAAVLBLMASK	(1 << 21)
126 127
#define MCI_SDIOITMASK		(1 << 22)
#define MCI_CEATAENDMASK	(1 << 23)
L
Linus Torvalds 已提交
128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155

#define MMCIMASK1		0x040
#define MMCIFIFOCNT		0x048
#define MMCIFIFO		0x080 /* to 0x0bc */

#define MCI_IRQENABLE	\
	(MCI_CMDCRCFAILMASK|MCI_DATACRCFAILMASK|MCI_CMDTIMEOUTMASK|	\
	MCI_DATATIMEOUTMASK|MCI_TXUNDERRUNMASK|MCI_RXOVERRUNMASK|	\
	MCI_CMDRESPENDMASK|MCI_CMDSENTMASK|MCI_DATABLOCKENDMASK)

/*
 * The size of the FIFO in bytes.
 */
#define MCI_FIFOSIZE	(16*4)
	
#define MCI_FIFOHALFSIZE (MCI_FIFOSIZE / 2)

#define NR_SG		16

struct clk;

struct mmci_host {
	void __iomem		*base;
	struct mmc_request	*mrq;
	struct mmc_command	*cmd;
	struct mmc_data		*data;
	struct mmc_host		*mmc;
	struct clk		*clk;
156 157
	int			gpio_cd;
	int			gpio_wp;
L
Linus Torvalds 已提交
158 159 160 161 162 163 164 165

	unsigned int		data_xfered;

	spinlock_t		lock;

	unsigned int		mclk;
	unsigned int		cclk;
	u32			pwr;
166
	struct mmci_platform_data *plat;
L
Linus Torvalds 已提交
167

168 169 170
	u8			hw_designer;
	u8			hw_revision:4;

L
Linus Torvalds 已提交
171 172 173 174 175 176 177 178 179
	struct timer_list	timer;
	unsigned int		oldstat;

	unsigned int		sg_len;

	/* pio stuff */
	struct scatterlist	*sg_ptr;
	unsigned int		sg_off;
	unsigned int		size;
180
	struct regulator	*vcc;
L
Linus Torvalds 已提交
181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204
};

static inline void mmci_init_sg(struct mmci_host *host, struct mmc_data *data)
{
	/*
	 * Ideally, we want the higher levels to pass us a scatter list.
	 */
	host->sg_len = data->sg_len;
	host->sg_ptr = data->sg;
	host->sg_off = 0;
}

static inline int mmci_next_sg(struct mmci_host *host)
{
	host->sg_ptr++;
	host->sg_off = 0;
	return --host->sg_len;
}

static inline char *mmci_kmap_atomic(struct mmci_host *host, unsigned long *flags)
{
	struct scatterlist *sg = host->sg_ptr;

	local_irq_save(*flags);
E
Emil Medve 已提交
205
	return kmap_atomic(sg_page(sg), KM_BIO_SRC_IRQ) + sg->offset;
L
Linus Torvalds 已提交
206 207
}

208
static inline void mmci_kunmap_atomic(struct mmci_host *host, void *buffer, unsigned long *flags)
L
Linus Torvalds 已提交
209
{
210
	kunmap_atomic(buffer, KM_BIO_SRC_IRQ);
L
Linus Torvalds 已提交
211 212
	local_irq_restore(*flags);
}