docg3.h 10.3 KB
Newer Older
R
Robert Jarzmik 已提交
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24
/*
 * Handles the M-Systems DiskOnChip G3 chip
 *
 * Copyright (C) 2011 Robert Jarzmik
 *
 * This program is free software; you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation; either version 2 of the License, or
 * (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program; if not, write to the Free Software
 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
 *
 */

#ifndef _MTD_DOCG3_H
#define _MTD_DOCG3_H

25 26
#include <linux/mtd/mtd.h>

R
Robert Jarzmik 已提交
27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55
/*
 * Flash memory areas :
 *   - 0x0000 .. 0x07ff : IPL
 *   - 0x0800 .. 0x0fff : Data area
 *   - 0x1000 .. 0x17ff : Registers
 *   - 0x1800 .. 0x1fff : Unknown
 */
#define DOC_IOSPACE_IPL			0x0000
#define DOC_IOSPACE_DATA		0x0800
#define DOC_IOSPACE_SIZE		0x2000

/*
 * DOC G3 layout and adressing scheme
 *   A page address for the block "b", plane "P" and page "p":
 *   address = [bbbb bPpp pppp]
 */

#define DOC_ADDR_PAGE_MASK		0x3f
#define DOC_ADDR_BLOCK_SHIFT		6
#define DOC_LAYOUT_NBPLANES		2
#define DOC_LAYOUT_PAGES_PER_BLOCK	64
#define DOC_LAYOUT_PAGE_SIZE		512
#define DOC_LAYOUT_OOB_SIZE		16
#define DOC_LAYOUT_WEAR_SIZE		8
#define DOC_LAYOUT_PAGE_OOB_SIZE				\
	(DOC_LAYOUT_PAGE_SIZE + DOC_LAYOUT_OOB_SIZE)
#define DOC_LAYOUT_WEAR_OFFSET		(DOC_LAYOUT_PAGE_OOB_SIZE * 2)
#define DOC_LAYOUT_BLOCK_SIZE					\
	(DOC_LAYOUT_PAGES_PER_BLOCK * DOC_LAYOUT_PAGE_SIZE)
56 57 58 59 60 61 62

/*
 * ECC related constants
 */
#define DOC_ECC_BCH_M			14
#define DOC_ECC_BCH_T			4
#define DOC_ECC_BCH_PRIMPOLY		0x4443
R
Robert Jarzmik 已提交
63 64 65
#define DOC_ECC_BCH_SIZE		7
#define DOC_ECC_BCH_COVERED_BYTES				\
	(DOC_LAYOUT_PAGE_SIZE + DOC_LAYOUT_OOB_PAGEINFO_SZ +	\
66 67 68
	 DOC_LAYOUT_OOB_HAMMING_SZ)
#define DOC_ECC_BCH_TOTAL_BYTES					\
	(DOC_ECC_BCH_COVERED_BYTES + DOC_LAYOUT_OOB_BCH_SZ)
R
Robert Jarzmik 已提交
69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93

/*
 * Blocks distribution
 */
#define DOC_LAYOUT_BLOCK_BBT		0
#define DOC_LAYOUT_BLOCK_OTP		0
#define DOC_LAYOUT_BLOCK_FIRST_DATA	6

#define DOC_LAYOUT_PAGE_BBT		4

/*
 * Extra page OOB (16 bytes wide) layout
 */
#define DOC_LAYOUT_OOB_PAGEINFO_OFS	0
#define DOC_LAYOUT_OOB_HAMMING_OFS	7
#define DOC_LAYOUT_OOB_BCH_OFS		8
#define DOC_LAYOUT_OOB_UNUSED_OFS	15
#define DOC_LAYOUT_OOB_PAGEINFO_SZ	7
#define DOC_LAYOUT_OOB_HAMMING_SZ	1
#define DOC_LAYOUT_OOB_BCH_SZ		7
#define DOC_LAYOUT_OOB_UNUSED_SZ	1


#define DOC_CHIPID_G3			0x200
#define DOC_ERASE_MARK			0xaa
94
#define DOC_MAX_NBFLOORS		4
R
Robert Jarzmik 已提交
95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119
/*
 * Flash registers
 */
#define DOC_CHIPID			0x1000
#define DOC_TEST			0x1004
#define DOC_BUSLOCK			0x1006
#define DOC_ENDIANCONTROL		0x1008
#define DOC_DEVICESELECT		0x100a
#define DOC_ASICMODE			0x100c
#define DOC_CONFIGURATION		0x100e
#define DOC_INTERRUPTCONTROL		0x1010
#define DOC_READADDRESS			0x101a
#define DOC_DATAEND			0x101e
#define DOC_INTERRUPTSTATUS		0x1020

#define DOC_FLASHSEQUENCE		0x1032
#define DOC_FLASHCOMMAND		0x1034
#define DOC_FLASHADDRESS		0x1036
#define DOC_FLASHCONTROL		0x1038
#define DOC_NOP				0x103e

#define DOC_ECCCONF0			0x1040
#define DOC_ECCCONF1			0x1042
#define DOC_ECCPRESET			0x1044
#define DOC_HAMMINGPARITY		0x1046
R
Robert Jarzmik 已提交
120
#define DOC_BCH_HW_ECC(idx)		(0x1048 + idx)
R
Robert Jarzmik 已提交
121 122

#define DOC_PROTECTION			0x1056
123 124
#define DOC_DPS0_KEY			0x105c
#define DOC_DPS1_KEY			0x105e
R
Robert Jarzmik 已提交
125 126 127 128 129 130 131 132 133
#define DOC_DPS0_ADDRLOW		0x1060
#define DOC_DPS0_ADDRHIGH		0x1062
#define DOC_DPS1_ADDRLOW		0x1064
#define DOC_DPS1_ADDRHIGH		0x1066
#define DOC_DPS0_STATUS			0x106c
#define DOC_DPS1_STATUS			0x106e

#define DOC_ASICMODECONFIRM		0x1072
#define DOC_CHIPID_INV			0x1074
134
#define DOC_POWERMODE			0x107c
R
Robert Jarzmik 已提交
135 136 137 138 139 140 141

/*
 * Flash sequences
 * A sequence is preset before one or more commands are input to the chip.
 */
#define DOC_SEQ_RESET			0x00
#define DOC_SEQ_PAGE_SIZE_532		0x03
R
Robert Jarzmik 已提交
142 143
#define DOC_SEQ_SET_FASTMODE		0x05
#define DOC_SEQ_SET_RELIABLEMODE	0x09
R
Robert Jarzmik 已提交
144 145 146 147
#define DOC_SEQ_READ			0x12
#define DOC_SEQ_SET_PLANE1		0x0e
#define DOC_SEQ_SET_PLANE2		0x10
#define DOC_SEQ_PAGE_SETUP		0x1d
148 149
#define DOC_SEQ_ERASE			0x27
#define DOC_SEQ_PLANES_STATUS		0x31
R
Robert Jarzmik 已提交
150 151 152 153 154 155 156 157 158 159 160 161 162 163

/*
 * Flash commands
 */
#define DOC_CMD_READ_PLANE1		0x00
#define DOC_CMD_SET_ADDR_READ		0x05
#define DOC_CMD_READ_ALL_PLANES		0x30
#define DOC_CMD_READ_PLANE2		0x50
#define DOC_CMD_READ_FLASH		0xe0
#define DOC_CMD_PAGE_SIZE_532		0x3c

#define DOC_CMD_PROG_BLOCK_ADDR		0x60
#define DOC_CMD_PROG_CYCLE1		0x80
#define DOC_CMD_PROG_CYCLE2		0x10
164
#define DOC_CMD_PROG_CYCLE3		0x11
R
Robert Jarzmik 已提交
165
#define DOC_CMD_ERASECYCLE2		0xd0
166 167
#define DOC_CMD_READ_STATUS		0x70
#define DOC_CMD_PLANES_STATUS		0x71
R
Robert Jarzmik 已提交
168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197

#define DOC_CMD_RELIABLE_MODE		0x22
#define DOC_CMD_FAST_MODE		0xa2

#define DOC_CMD_RESET			0xff

/*
 * Flash register : DOC_FLASHCONTROL
 */
#define DOC_CTRL_VIOLATION		0x20
#define DOC_CTRL_CE			0x10
#define DOC_CTRL_UNKNOWN_BITS		0x08
#define DOC_CTRL_PROTECTION_ERROR	0x04
#define DOC_CTRL_SEQUENCE_ERROR		0x02
#define DOC_CTRL_FLASHREADY		0x01

/*
 * Flash register : DOC_ASICMODE
 */
#define DOC_ASICMODE_RESET		0x00
#define DOC_ASICMODE_NORMAL		0x01
#define DOC_ASICMODE_POWERDOWN		0x02
#define DOC_ASICMODE_MDWREN		0x04
#define DOC_ASICMODE_BDETCT_RESET	0x08
#define DOC_ASICMODE_RSTIN_RESET	0x10
#define DOC_ASICMODE_RAM_WE		0x20

/*
 * Flash register : DOC_ECCCONF0
 */
R
Robert Jarzmik 已提交
198
#define DOC_ECCCONF0_WRITE_MODE		0x0000
R
Robert Jarzmik 已提交
199 200 201 202 203 204 205 206 207 208 209
#define DOC_ECCCONF0_READ_MODE		0x8000
#define DOC_ECCCONF0_AUTO_ECC_ENABLE	0x4000
#define DOC_ECCCONF0_HAMMING_ENABLE	0x1000
#define DOC_ECCCONF0_BCH_ENABLE		0x0800
#define DOC_ECCCONF0_DATA_BYTES_MASK	0x07ff

/*
 * Flash register : DOC_ECCCONF1
 */
#define DOC_ECCCONF1_BCH_SYNDROM_ERR	0x80
#define DOC_ECCCONF1_UNKOWN1		0x40
210
#define DOC_ECCCONF1_PAGE_IS_WRITTEN	0x20
R
Robert Jarzmik 已提交
211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247
#define DOC_ECCCONF1_UNKOWN3		0x10
#define DOC_ECCCONF1_HAMMING_BITS_MASK	0x0f

/*
 * Flash register : DOC_PROTECTION
 */
#define DOC_PROTECT_FOUNDRY_OTP_LOCK	0x01
#define DOC_PROTECT_CUSTOMER_OTP_LOCK	0x02
#define DOC_PROTECT_LOCK_INPUT		0x04
#define DOC_PROTECT_STICKY_LOCK		0x08
#define DOC_PROTECT_PROTECTION_ENABLED	0x10
#define DOC_PROTECT_IPL_DOWNLOAD_LOCK	0x20
#define DOC_PROTECT_PROTECTION_ERROR	0x80

/*
 * Flash register : DOC_DPS0_STATUS and DOC_DPS1_STATUS
 */
#define DOC_DPS_OTP_PROTECTED		0x01
#define DOC_DPS_READ_PROTECTED		0x02
#define DOC_DPS_WRITE_PROTECTED		0x04
#define DOC_DPS_HW_LOCK_ENABLED		0x08
#define DOC_DPS_KEY_OK			0x80

/*
 * Flash register : DOC_CONFIGURATION
 */
#define DOC_CONF_IF_CFG			0x80
#define DOC_CONF_MAX_ID_MASK		0x30
#define DOC_CONF_VCCQ_3V		0x01

/*
 * Flash register : DOC_READADDRESS
 */
#define DOC_READADDR_INC		0x8000
#define DOC_READADDR_ONE_BYTE		0x4000
#define DOC_READADDR_ADDR_MASK		0x1fff

248 249 250 251 252
/*
 * Flash register : DOC_POWERMODE
 */
#define DOC_POWERDOWN_READY		0x80

253 254 255 256 257 258 259
/*
 * Status of erase and write operation
 */
#define DOC_PLANES_STATUS_FAIL		0x01
#define DOC_PLANES_STATUS_PLANE0_KO	0x02
#define DOC_PLANES_STATUS_PLANE1_KO	0x04

260 261 262 263 264 265 266 267 268 269 270
/*
 * DPS key management
 *
 * Each floor of docg3 has 2 protection areas: DPS0 and DPS1. These areas span
 * across block boundaries, and define whether these blocks can be read or
 * written.
 * The definition is dynamically stored in page 0 of blocks (2,3) for DPS0, and
 * page 0 of blocks (4,5) for DPS1.
 */
#define DOC_LAYOUT_DPS_KEY_LENGTH	8

271 272 273 274 275
/**
 * struct docg3_cascade - Cascade of 1 to 4 docg3 chips
 * @floors: floors (ie. one physical docg3 chip is one floor)
 * @base: IO space to access all chips in the cascade
 * @bch: the BCH correcting control structure
276
 * @lock: lock to protect docg3 IO space from concurrent accesses
277 278 279 280 281
 */
struct docg3_cascade {
	struct mtd_info *floors[DOC_MAX_NBFLOORS];
	void __iomem *base;
	struct bch_control *bch;
282
	struct mutex lock;
283 284
};

R
Robert Jarzmik 已提交
285 286 287
/**
 * struct docg3 - DiskOnChip driver private data
 * @dev: the device currently under control
288
 * @cascade: the cascade this device belongs to
R
Robert Jarzmik 已提交
289 290
 * @device_id: number of the cascaded DoCG3 device (0, 1, 2 or 3)
 * @if_cfg: if true, reads are on 16bits, else reads are on 8bits
R
Robert Jarzmik 已提交
291 292 293 294 295

 * @reliable: if 0, docg3 in normal mode, if 1 docg3 in fast mode, if 2 in
 *            reliable mode
 *            Fast mode implies more errors than normal mode.
 *            Reliable mode implies that page 2*n and 2*n+1 are clones.
R
Robert Jarzmik 已提交
296
 * @bbt: bad block table cache
297 298 299 300 301
 * @oob_write_ofs: offset of the MTD where this OOB should belong (ie. in next
 *                 page_write)
 * @oob_autoecc: if 1, use only bytes 0-7, 15, and fill the others with HW ECC
 *               if 0, use all the 16 bytes.
 * @oob_write_buf: prepared OOB for next page_write
R
Robert Jarzmik 已提交
302 303 304 305
 * @debugfs_root: debugfs root node
 */
struct docg3 {
	struct device *dev;
306
	struct docg3_cascade *cascade;
R
Robert Jarzmik 已提交
307 308
	unsigned int device_id:4;
	unsigned int if_cfg:1;
R
Robert Jarzmik 已提交
309
	unsigned int reliable:2;
R
Robert Jarzmik 已提交
310 311
	int max_block;
	u8 *bbt;
312 313 314
	loff_t oob_write_ofs;
	int oob_autoecc;
	u8 oob_write_buf[DOC_LAYOUT_OOB_SIZE];
R
Robert Jarzmik 已提交
315 316 317 318 319 320 321 322 323 324 325 326 327 328 329 330 331 332 333 334 335 336 337 338 339 340 341 342 343 344 345 346 347 348 349 350 351 352 353 354 355 356 357 358 359 360 361 362 363 364 365 366 367 368 369 370
	struct dentry *debugfs_root;
};

#define doc_err(fmt, arg...) dev_err(docg3->dev, (fmt), ## arg)
#define doc_info(fmt, arg...) dev_info(docg3->dev, (fmt), ## arg)
#define doc_dbg(fmt, arg...) dev_dbg(docg3->dev, (fmt), ## arg)
#define doc_vdbg(fmt, arg...) dev_vdbg(docg3->dev, (fmt), ## arg)

#define DEBUGFS_RO_ATTR(name, show_fct) \
	static int name##_open(struct inode *inode, struct file *file) \
	{ return single_open(file, show_fct, inode->i_private); }      \
	static const struct file_operations name##_fops = { \
		.owner = THIS_MODULE, \
		.open = name##_open, \
		.llseek = seq_lseek, \
		.read = seq_read, \
		.release = single_release \
	};
#endif

/*
 * Trace events part
 */
#undef TRACE_SYSTEM
#define TRACE_SYSTEM docg3

#if !defined(_MTD_DOCG3_TRACE) || defined(TRACE_HEADER_MULTI_READ)
#define _MTD_DOCG3_TRACE

#include <linux/tracepoint.h>

TRACE_EVENT(docg3_io,
	    TP_PROTO(int op, int width, u16 reg, int val),
	    TP_ARGS(op, width, reg, val),
	    TP_STRUCT__entry(
		    __field(int, op)
		    __field(unsigned char, width)
		    __field(u16, reg)
		    __field(int, val)),
	    TP_fast_assign(
		    __entry->op = op;
		    __entry->width = width;
		    __entry->reg = reg;
		    __entry->val = val;),
	    TP_printk("docg3: %s%02d reg=%04x, val=%04x",
		      __entry->op ? "write" : "read", __entry->width,
		      __entry->reg, __entry->val)
	);
#endif

/* This part must be outside protection */
#undef TRACE_INCLUDE_PATH
#undef TRACE_INCLUDE_FILE
#define TRACE_INCLUDE_PATH .
#define TRACE_INCLUDE_FILE docg3
#include <trace/define_trace.h>