-/* $OpenBSD: ufshci.c,v 1.31 2024/05/24 09:51:14 mglocker Exp $ */
+/* $OpenBSD: ufshci.c,v 1.32 2024/05/24 20:34:06 mglocker Exp $ */
/*
* Copyright (c) 2022 Marcus Glocker <mglocker@openbsd.org>
ufshci_intr(void *arg)
{
struct ufshci_softc *sc = arg;
- uint32_t status;
+ uint32_t status, hcs;
int handled = 0;
status = UFSHCI_READ_4(sc, UFSHCI_REG_IS);
handled = 1;
}
+ /* If Auto-Hibernate raises an interrupt, it's to yield an error. */
+ if (status & UFSHCI_REG_IS_UHES) {
+ hcs = UFSHCI_READ_4(sc, UFSHCI_REG_HCS);
+ printf("%s: Auto-Hibernate enter error UPMCRS=0x%x\n",
+ __func__, UFSHCI_REG_HCS_UPMCRS(hcs));
+ }
+ if (status & UFSHCI_REG_IS_UHXS) {
+ hcs = UFSHCI_READ_4(sc, UFSHCI_REG_HCS);
+ printf("%s: Auto-Hibernate exit error UPMCRS=0x%x\n",
+ __func__, UFSHCI_REG_HCS_UPMCRS(hcs));
+ }
if (handled == 0) {
printf("%s: UNKNOWN interrupt, status=0x%08x\n",
return 1;
}
+ /* Enable Auto-Hibernate Idle Timer (AHIT) and set it to 150ms. */
+ if (sc->sc_cap & UFSHCI_REG_AUTOH8) {
+ UFSHCI_WRITE_4(sc, UFSHCI_REG_AHIT,
+ UFSHCI_REG_AHIT_TS(UFSHCI_REG_AHIT_TS_1MS) | 150);
+ }
+
/* Attach to SCSI layer */
saa.saa_adapter = &ufshci_switch;
saa.saa_adapter_softc = sc;
*/
/* 7.1.1 Host Controller Initialization: 5) */
- UFSHCI_WRITE_4(sc, UFSHCI_REG_IE,
- UFSHCI_REG_IE_UTRCE | UFSHCI_REG_IE_UTMRCE);
+ if (sc->sc_cap & UFSHCI_REG_AUTOH8) {
+ UFSHCI_WRITE_4(sc, UFSHCI_REG_IE,
+ UFSHCI_REG_IE_UTRCE | UFSHCI_REG_IE_UTMRCE |
+ UFSHCI_REG_IS_UHES | UFSHCI_REG_IS_UHXS);
+ } else {
+ UFSHCI_WRITE_4(sc, UFSHCI_REG_IE,
+ UFSHCI_REG_IE_UTRCE | UFSHCI_REG_IE_UTMRCE);
+ }
/* 7.1.1 Host Controller Initialization: 6) */
UFSHCI_WRITE_4(sc, UFSHCI_REG_UICCMD,
-/* $OpenBSD: ufshcireg.h,v 1.12 2024/05/24 09:51:14 mglocker Exp $ */
+/* $OpenBSD: ufshcireg.h,v 1.13 2024/05/24 20:34:06 mglocker Exp $ */
/*
* Copyright (c) 2022 Marcus Glocker <mglocker@openbsd.org>
#define UFSHCI_REG_HCMID_MIC(x) ((x >> 0) & 0x000000ff) /* RO */
/* Auto-Hibernate Idle Timer */
#define UFSHCI_REG_AHIT 0x18
+#define UFSHCI_REG_AHIT_TS(x) (x << 10)
+#define UFSHCI_REG_AHIT_TS_1US 0x00
+#define UFSHCI_REG_AHIT_TS_10US 0x01
+#define UFSHCI_REG_AHIT_TS_100US 0x02
+#define UFSHCI_REG_AHIT_TS_1MS 0x03
+#define UFSHCI_REG_AHIT_TS_10MS 0x04
+#define UFSHCI_REG_AHIT_TS_100MS 0x05
/*
* Operation and Runtime Registers