summaryrefslogtreecommitdiff
path: root/sys/dev/ic/ufshcireg.h
blob: 688d66962235f4590bf751fa5b50d893881a80dd (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
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
56
57
58
59
60
61
62
63
64
65
66
67
68
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
94
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
120
121
122
123
124
125
126
127
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
156
157
158
159
160
161
162
163
164
165
166
167
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
198
199
200
201
202
203
204
205
206
207
208
209
210
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
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
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
/*	$OpenBSD: ufshcireg.h,v 1.7 2024/05/09 08:20:22 mglocker Exp $ */

/*
 * Copyright (c) 2022 Marcus Glocker <mglocker@openbsd.org>
 *
 * Permission to use, copy, modify, and distribute this software for any
 * purpose with or without fee is hereby granted, provided that the above
 * copyright notice and this permission notice appear in all copies.
 *
 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
 */

/*
 * Generic parameters.
 */
#define UFSHCI_UCD_PRDT_MAX_SEGS	64
#define UFSHCI_UCD_PRDT_MAX_XFER	(UFSHCI_UCD_PRDT_MAX_SEGS * PAGE_SIZE)
#define UFSHCI_INTR_AGGR_TIMEOUT	0x64 /* 4ms */
#define UFSHCI_MAX_UNITS		32

/*
 * Controller Capabilities Registers
 */

/* Controller Capabilities */
#define UFSHCI_REG_CAP			0x00
#define  UFSHCI_REG_CAP_CS		(1 << 28) /* RO */
#define  UFSHCI_REG_CAP_UICDMETMS	(1 << 26) /* RO */
#define  UFSHCI_REG_CAP_OODDS		(1 << 25) /* RO */
#define  UFSHCI_REG_CAP_64AS		(1 << 24) /* RO */
#define  UFSHCI_REG_AUTOH8		(1 << 23) /* RO */
#define  UFSHCI_REG_CAP_NUTMRS(x)	((x >> 16) & 0x00000007) /* RO */
#define  UFSHCI_REG_CAP_RTT(x)		((x >>  8) & 0x000000ff) /* RO */
#define  UFSHCI_REG_CAP_NUTRS(x)	((x >>  0) & 0x0000001f) /* RO */
/* UFS Version in BCD format */
#define UFSHCI_REG_VER			0x08
#define  UFSHCI_REG_VER_MAJOR(x)	((x >> 8) & 0x0000000f) /* RO */
#define  UFSHCI_REG_VER_MINOR(x)	((x >> 4) & 0x0000000f) /* RO */
#define  UFSHCI_REG_VER_SUFFIX(x)	((x >> 0) & 0x0000000f) /* RO */
/* Product ID */
#define UFSHCI_REG_HCPID		0x10
/* Manufacturer ID */
#define UFSHCI_REG_HCMID		0x14
#define  UFSHCI_REG_HCMID_BI(x)		((x >> 8) & 0x000000ff) /* RO */
#define  UFSHCI_REG_HCMID_MIC(x)	((x >> 0) & 0x000000ff) /* RO */
/* Auto-Hibernate Idle Timer */
#define UFSHCI_REG_AHIT			0x18

/*
 * Operation and Runtime Registers
 */

/* Interrupt Status */
#define UFSHCI_REG_IS			0x20
#define  UFSHCI_REG_IS_CEFES		(1 << 18) /* RWC */
#define  UFSHCI_REG_IS_SBFES		(1 << 17) /* RWC */
#define  UFSHCI_REG_IS_HCFES		(1 << 16) /* RWC */
#define  UFSHCI_REG_IS_UTPES		(1 << 12) /* RWC */
#define  UFSHCI_REG_IS_DFES		(1 << 11) /* RWC */
#define  UFSHCI_REG_IS_UCCS		(1 << 10) /* RWC */
#define  UFSHCI_REG_IS_UTMRCS		(1 <<  9) /* RWC */
#define  UFSHCI_REG_IS_ULSS		(1 <<  8) /* RWC */
#define  UFSHCI_REG_IS_ULLS		(1 <<  7) /* RWC */
#define  UFSHCI_REG_IS_UHES		(1 <<  6) /* RWC */
#define  UFSHCI_REG_IS_UHXS		(1 <<  5) /* RWC */
#define  UFSHCI_REG_IS_UPMS		(1 <<  4) /* RWC */
#define  UFSHCI_REG_IS_UTMS		(1 <<  3) /* RWC */
#define  UFSHCI_REG_IS_UE		(1 <<  2) /* RWC */
#define  UFSHCI_REG_IS_UDEPRI		(1 <<  1) /* RWC */
#define  UFSHCI_REG_IS_UTRCS		(1 <<  0) /* RWC */
/* Interrupt Enable */
#define UFSHCI_REG_IE			0x24
#define  UFSHCI_REG_IE_CEFFE		(1 << 18) /* RW */
#define  UFSHCI_REG_IE_SBFEE		(1 << 17) /* RW */
#define  UFSHCI_REG_IE_HCFEE		(1 << 16) /* RW */
#define  UFSHCI_REG_IE_UTPEE		(1 << 12) /* RW */
#define  UFSHCI_REG_IE_DFEE		(1 << 11) /* RW */
#define  UFSHCI_REG_IE_UCCE		(1 << 10) /* RW */
#define  UFSHCI_REG_IE_UTMRCE		(1 <<  9) /* RW */
#define  UFSHCI_REG_IE_ULSSE		(1 <<  8) /* RW */
#define  UFSHCI_REG_IE_ULLSE		(1 <<  7) /* RW */
#define  UFSHCI_REG_IE_UHESE		(1 <<  6) /* RW */
#define  UFSHCI_REG_IE_UHXSE		(1 <<  5) /* RW */
#define  UFSHCI_REG_IE_UPMSE		(1 <<  4) /* RW */
#define  UFSHCI_REG_IE_UTMSE		(1 <<  3) /* RW */
#define  UFSHCI_REG_IE_UEE		(1 <<  2) /* RW */
#define  UFSHCI_REG_IE_UDEPRIE		(1 <<  1) /* RW */
#define  UFSHCI_REG_IE_UTRCE		(1 <<  0) /* RW */
/* Host Controller Status */
#define UFSHCI_REG_HCS			0x30
#define  UFSHCI_REG_HCS_TLUNUTPE(x)	((x << 24) & 0xff000000) /* RO */
#define  UFSHCI_REG_HCS_TTAGUTPE(x)	((x << 16) & 0x00ff0000) /* RO */
#define  UFSHCI_REG_HCS_UTPEC(x)	((x << 12) & 0x0000f000) /* RO */
#define  UFSHCI_REG_HCS_UPMCRS(x)	((x <<  8) & 0x00000700) /* RO */
#define  UFSHCI_REG_HCS_UCRDY		(1 << 3) /* RO */
#define  UFSHCI_REG_HCS_UTMRLRDY	(1 << 2) /* RO */
#define  UFSHCI_REG_HCS_UTRLRDY		(1 << 1) /* RO */
#define  UFSHCI_REG_HCS_DP		(1 << 0) /* RO */
/* Host Controller Enable */
#define UFSHCI_REG_HCE			0x34
#define  UFSHCI_REG_HCE_CGE		(1 << 1) /* RW */
#define  UFSHCI_REG_HCE_HCE		(1 << 0) /* RW */
/* Host UIC Error Code PHY Adapter Layer */
#define UFSHCI_REG_UECPA		0x38
/* Host UIC Error Code Data Link Layer */
#define UFSHCI_REG_UECDL		0x3C
/* Host UIC Error Code Network Layer */
#define UFSHCI_REG_UECN			0x40
/* Host UIC Error Code Transport Layer */
#define UFSHCI_REG_UECT			0x44
/* Host UIC Error Code */
#define UFSHCI_REG_UECDME		0x48
/* UTP Transfer Request Interrupt Aggregation Control Register */
#define UFSHCI_REG_UTRIACR		0x4C
#define  UFSHCI_REG_UTRIACR_IAEN	(1U << 31) /* RW */
#define  UFSHCI_REG_UTRIACR_IAPWEN	(1 << 24) /* WO */
#define  UFSHCI_REG_UTRIACR_IASB	(1 << 20) /* RO */
#define  UFSHCI_REG_UTRIACR_CTR		(1 << 16) /* WO */
#define  UFSHCI_REG_UTRIACR_IACTH(x)	(x <<  8) /* RW, max. val = 31 */
#define  UFSHCI_REG_UTRIACR_IATOVAL(x)	(x <<  0) /* RW, 40us units (1=40us) */

/*
 * UTP Transfer Request List Registers
 */

/* Base Address */
#define UFSHCI_REG_UTRLBA			0x50 /* RW */
/* Base Address Upper 32-bits */
#define UFSHCI_REG_UTRLBAU			0x54 /* RW */
/* Door Bell Register */
#define UFSHCI_REG_UTRLDBR			0x58 /* RWS */
/* Clear Register */
#define UFSHCI_REG_UTRLCLR			0x5C /* WO */
/* Run-Stop Register */
#define UFSHCI_REG_UTRLRSR			0x60 /* RW */
#define  UFSHCI_REG_UTRLRSR_STOP		0x00
#define  UFSHCI_REG_UTRLRSR_START		0x01
/* Completion Notification Register */
#define UFSHCI_REG_UTRLCNR			0x64 /* RWC */

/*
 * UTP Task Management Request List Registers
 */

/* Base Address */
#define UFSHCI_REG_UTMRLBA			0x70 /* RW */
/* Base Address Upper 32-bits */
#define UFSHCI_REG_UTMRLBAU			0x74 /* RW */
/* Door Bell Register */
#define UFSHCI_REG_UTMRLDBR			0x78 /* RWS */
/* Clear Register */
#define UFSHCI_REG_UTMRLCLR			0x7C /* WO */
/* Run-Stop Register */
#define UFSHCI_REG_UTMRLRSR			0x80 /* RW */
#define  UFSHCI_REG_UTMRLRSR_STOP		0x00
#define  UFSHCI_REG_UTMRLRSR_START		0x01

/*
 * UIC Command Registers
 */

/* UIC Command Register */
#define UFSHCI_REG_UICCMD				0x90
#define  UFSHCI_REG_UICCMD_CMDOP_DME_GET		0x01 /* RW */
#define  UFSHCI_REG_UICCMD_CMDOP_DME_SET		0x02 /* RW */
#define  UFSHCI_REG_UICCMD_CMDOP_DME_PEER_GET		0x03 /* RW */
#define  UFSHCI_REG_UICCMD_CMDOP_DME_PEER_SET		0x04 /* RW */
#define  UFSHCI_REG_UICCMD_CMDOP_DME_POWERON		0x10 /* RW */
#define  UFSHCI_REG_UICCMD_CMDOP_DME_POWEROFF		0x11 /* RW */
#define  UFSHCI_REG_UICCMD_CMDOP_DME_ENABLE		0x12 /* RW */
#define  UFSHCI_REG_UICCMD_CMDOP_DME_RESET		0x14 /* RW */
#define  UFSHCI_REG_UICCMD_CMDOP_DME_ENDPOINTRESET	0x15 /* RW */
#define  UFSHCI_REG_UICCMD_CMDOP_DME_LINKSTARTUP	0x16 /* RW */
#define  UFSHCI_REG_UICCMD_CMDOP_DME_HIBERNATE_ENTER	0x17 /* RW */
#define  UFSHCI_REG_UICCMD_CMDOP_DME_HIBERNATE_EXIT	0x18 /* RW */
#define  UFSHCI_REG_UICCMD_CMDOP_DME_TEST_MODE		0x1A /* RW */
/* UIC Command Argument 1 */
#define UFSHCI_REG_UICCMDARG1				0x94
/* UIC Command Argument 2 */
#define UFSHCI_REG_UICCMDARG2				0x98
/* UIC Command Argument 3 */
#define UFSHCI_REG_UICCMDARG3				0x9C

/*
 * Vendor Specific Registers (0xC0 - 0xFF)
 */

/*
 * UTP Transfer Request Descriptor Structure
 */

/* Command Type (CT) */
#define UFSHCI_UTRD_DW0_CT_UFS		(1 << 28) /* UFS Storage */
/* Data Direction (DD) */
#define UFSHCI_UTRD_DW0_DD_NO		(0 << 25) /* No transfer */
#define UFSHCI_UTRD_DW0_DD_I2T		(1 << 25) /* From Initiator to Target */
#define UFSHCI_UTRD_DW0_DD_T2I		(2 << 25) /* From Target to Initiator */
/* Interrupt (I) */
#define UFSHCI_UTRD_DW0_I_REG		(0 << 24) /* Regular Command */
#define UFSHCI_UTRD_DW0_I_INT		(1 << 24) /* Interrupt Command */
/* Crypto Enable (CE) */
#define UFSHCI_UTRD_DW0_CE_DISABLE	(0 << 23) /* Disable Crypto */
#define UFSHCI_UTRD_DW0_CE_ENABLE	(1 << 23) /* Enable Crypto */
/* Crypto Configuration Index (CCI) */
#define UFSHCI_UTRD_DW0_CCI(x)		(x & 0x000000ff)

/* Data Unit Number Upper 32-bits (DUNL) */
#define UFSHCI_UTRD_DW1_DUNL(x)		(x << 0)

/* Overall Command Status (OCS) */
#define UFSHCI_UTRD_DW2_OCS(x)		(x & 0x000000ff)
#define UFSHCI_UTRD_DW2_OCS_SUCCESS	0x00 /* Success */
#define UFSHCI_UTRD_DW2_OCS_ICTA	0x01 /* Invalid Command Table Attr. */
#define UFSHCI_UTRD_DW2_OCS_IPA		0x02 /* Invalid PRDT Attr. */
#define UFSHCI_UTRD_DW2_OCS_MDBS	0x03 /* Mismatch Data Buffer Size */
#define UFSHCI_UTRD_DW2_OCS_MRUS	0x04 /* Mismatch Response UPIU Size */
#define UFSHCI_UTRD_DW2_OCS_CF		0x05 /* Communication Failure */
#define UFSHCI_UTRD_DW2_OCS_ABRT	0x06 /* Aborted */
#define UFSHCI_UTRD_DW2_OCS_FE		0x07 /* Fatal Error */
#define UFSHCI_UTRD_DW2_OCS_DFE		0x08 /* Device Fatal Error */
#define UFSHCI_UTRD_DW2_OCS_ICC		0x09 /* Invalid Crypto Configuration */
#define UFSHCI_UTRD_DW2_OCS_GCE		0x0A /* General Crypto Error */
#define UFSHCI_UTRD_DW2_OCS_IOV		0x0F /* Invalid OCS Value */

/* Data Unit Number Upper 32-bits Upper 32-bits (DUNU) */
#define UFSHCI_UTRD_DW3_DUNU(x)		(x << 0)

/* UTP Command Descriptor Base Address (UCDBA) */
#define UFSHCI_UTRD_DW4_UCDBA(x)	(x << 7)

/* UTP Command Descriptor Base Address Upper 32-bits (UCDBAU) */
#define UFSHCI_UTRD_DW5_UCDBAU(x)	(x << 0)

/* Response UPIU Offset (RUO) */
#define UFSHCI_UTRD_DW6_RUO(x)		(x << 16)
/* Response UPIU Length (RUL) */
#define UFSHCI_UTRD_DW6_RUL(x)		(x & 0x0000ffff)

/* PRDT Offset (PRDTO) */
#define UFSHCI_UTRD_DW7_PRDTO(x)	(x << 16)
/* PRDT Length (PRDTL) */
#define UFSHCI_UTRD_DW7_PRDTL(x)	(x & 0x0000ffff)

struct ufshci_utrd {
	uint32_t dw0; /* CT, DD, I, CE, CCI */
	uint32_t dw1; /* Data Unit Number Lower 32-bits (DUNL) */
	uint32_t dw2; /* OCS */
	uint32_t dw3; /* Data Unit Number Upper 32-bits (DUNU) */
	uint32_t dw4; /* UTP Cmd. Desc. Base Addr. Lower 32-bits (UCDBA) */
	uint32_t dw5; /* UTP Cmd. Desc. Base Addr. Upper 32-bits (UCDBAU) */
	uint32_t dw6; /* RUO, RUL */
	uint32_t dw7; /* PRDTO, PRDTL */
} __packed;

/*
 * UTP Command Descriptor, PRDT (Physical Region Description Table) Structure
 */

/* Data Base Address (DBA) */
#define UFSHCI_UCD_DW0_DBA(x)	(x & 0xfffffffc)

/* Data Byte Count (DBC) */
#define UFSHCI_UCD_DW3_DBC(x)	(x & 0x0003ffff)

struct ufshci_ucd_prdt {
	uint32_t dw0; /* Data base Address Lower 32-bits (DBA) */
	uint32_t dw1; /* Data base Address Upper 32-bits (DBAU) */
	uint32_t dw2; /* Reserved */
	uint32_t dw3; /* Data Byte Count (DBC) */
} __packed;

/*
 * UTP Task Management Request Descriptor Structure
 */

/* Interrupt (I) */
#define UFSHCI_UTMRD_DW0_I_DISABLE	(0 << 24)
#define UFSHCI_UTMRD_DW0_I_ENABLE	(1 << 24)

/* Overall Command Status (OCS) */
#define UFSHCI_UTMRD_DW2_OCS(x)		(x & 0x000000ff)
#define UFSHCI_UTMRD_DW2_OCS_SUCCESS	0x00 /* Success */
#define UFSHCI_UTMRD_DW2_OCS_ICTA	0x01 /* Invalid Command Table Attr. */
#define UFSHCI_UTMRD_DW2_OCS_IPA	0x02 /* Invalid PRDT Attr. */
#define UFSHCI_UTMRD_DW2_OCS_MDBS	0x03 /* Mismatch Data Buffer Size */
#define UFSHCI_UTMRD_DW2_OCS_MRUS	0x04 /* Mismatch Response UPIU Size */
#define UFSHCI_UTMRD_DW2_OCS_CF		0x05 /* Communication Failure */
#define UFSHCI_UTMRD_DW2_OCS_ABRT	0x06 /* Aborted */
#define UFSHCI_UTMRD_DW2_OCS_FE		0x07 /* Fatal Error */
#define UFSHCI_UTMRD_DW2_OCS_DFE	0x08 /* Device Fatal Error */
#define UFSHCI_UTMRD_DW2_OCS_ICC	0x09 /* Invalid Crypto Configuration */
#define UFSHCI_UTMRD_DW2_OCS_GCE	0x0A /* General Crypto Error */
#define UFSHCI_UTMRD_DW2_OCS_IOV	0x0F /* Invalid OCS Value */

struct ufshci_utmrd {
	uint32_t dw0; /* I */
	uint32_t dw1; /* Reserved */
	uint32_t dw2; /* OCS */
	uint32_t dw3; /* Reserved */
	uint8_t dw4_w11[32]; /* Task Management Request UPIU */
	uint8_t dw12_dw19[32]; /* Task Management Response UPIU */
} __packed;

/*
 * ****************************************************************************
 * Universal Flash Storage (UFS) Version 2.1 Specs from JESD220C
 * ****************************************************************************
 */

/* UPIU structures are in Big Endian! */

#define UPIU_TC_I2T_NOP_OUT		0x00
#define UPIU_TC_I2T_COMMAND		0x01
#define UPIU_TC_I2T_DATA_OUT		0x02
#define UPIU_TC_I2T_TMR			0x04
#define UPIU_TC_I2T_QUERY_REQUEST	0x16
#define UPIU_TC_T2I_NOP_IN		0x20
#define UPIU_TC_T2I_RESPONSE		0x21
#define UPIU_TC_T2I_DATA_IN		0x22
#define UPIU_TC_T2I_TMR			0x24
#define UPIU_TC_T2I_QUERY_RESPONSE	0x36
#define UPIU_TC_T2I_REJECT		0x3f

#define UPIU_SCSI_RSP_INQUIRY_SIZE	36
#define UPIU_SCSI_RSP_CAPACITY16_SIZE	32
#define UPIU_SCSI_RSP_CAPACITY_SIZE	8

struct upiu_hdr {
	uint8_t tc;			/* Transaction Code */
	uint8_t flags;
	uint8_t lun;
	uint8_t taskid;
	uint8_t cmd_set_type;
	uint8_t query;
	uint8_t response;
	uint8_t status;
	uint8_t ehs_len;
	uint8_t device_info;
	uint16_t ds_len;		/* Data Segment Length */
} __packed;

struct upiu_command {
	struct upiu_hdr hdr;
	uint32_t expected_xfer_len;
	uint8_t cdb[16];
} __packed;

struct upiu_response {
	struct upiu_hdr hdr;
	uint32_t residual_xfer_len;
	uint8_t cdb[16];
} __packed;

struct ufshci_ucd {
	struct upiu_command cmd;
	struct upiu_response rsp;
	struct ufshci_ucd_prdt prdt[UFSHCI_UCD_PRDT_MAX_SEGS];
} __packed __aligned(128);