u32 epctl_reg = dir_in ? S3C_DIEPCTL(idx) : S3C_DOEPCTL(idx);
u32 epsiz_reg = dir_in ? S3C_DIEPTSIZ(idx) : S3C_DOEPTSIZ(idx);
u32 ints;
- u32 clear = 0;
ints = readl(hsotg->regs + epint_reg);
+ /* Clear endpoint interrupts */
+ writel(ints, hsotg->regs + epint_reg);
+
dev_dbg(hsotg->dev, "%s: ep%d(%s) DxEPINT=0x%08x\n",
__func__, idx, dir_in ? "in" : "out", ints);
s3c_hsotg_handle_outdone(hsotg, idx, false);
}
-
- clear |= S3C_DxEPINT_XferCompl;
}
- if (ints & S3C_DxEPINT_EPDisbld) {
+ if (ints & S3C_DxEPINT_EPDisbld)
dev_dbg(hsotg->dev, "%s: EPDisbld\n", __func__);
- clear |= S3C_DxEPINT_EPDisbld;
- }
- if (ints & S3C_DxEPINT_AHBErr) {
+ if (ints & S3C_DxEPINT_AHBErr)
dev_dbg(hsotg->dev, "%s: AHBErr\n", __func__);
- clear |= S3C_DxEPINT_AHBErr;
- }
if (ints & S3C_DxEPINT_Setup) { /* Setup or Timeout */
dev_dbg(hsotg->dev, "%s: Setup/Timeout\n", __func__);
else
s3c_hsotg_handle_outdone(hsotg, 0, true);
}
-
- clear |= S3C_DxEPINT_Setup;
}
- if (ints & S3C_DxEPINT_Back2BackSetup) {
+ if (ints & S3C_DxEPINT_Back2BackSetup)
dev_dbg(hsotg->dev, "%s: B2BSetup/INEPNakEff\n", __func__);
- clear |= S3C_DxEPINT_Back2BackSetup;
- }
if (dir_in) {
/* not sure if this is important, but we'll clear it anyway
if (ints & S3C_DIEPMSK_INTknTXFEmpMsk) {
dev_dbg(hsotg->dev, "%s: ep%d: INTknTXFEmpMsk\n",
__func__, idx);
- clear |= S3C_DIEPMSK_INTknTXFEmpMsk;
}
/* this probably means something bad is happening */
if (ints & S3C_DIEPMSK_INTknEPMisMsk) {
dev_warn(hsotg->dev, "%s: ep%d: INTknEP\n",
__func__, idx);
- clear |= S3C_DIEPMSK_INTknEPMisMsk;
}
/* FIFO has space or is empty (see GAHBCFG) */
dev_dbg(hsotg->dev, "%s: ep%d: TxFIFOEmpty\n",
__func__, idx);
s3c_hsotg_trytx(hsotg, hs_ep);
- clear |= S3C_DIEPMSK_TxFIFOEmpty;
}
}
-
- writel(clear, hsotg->regs + epint_reg);
}
/**
dev_info(hsotg->dev, "OTGInt: %08x\n", otgint);
writel(otgint, hsotg->regs + S3C_GOTGINT);
- writel(S3C_GINTSTS_OTGInt, hsotg->regs + S3C_GINTSTS);
}
if (gintsts & S3C_GINTSTS_DisconnInt) {
}
if (gintsts & S3C_GINTSTS_EnumDone) {
- s3c_hsotg_irq_enumdone(hsotg);
writel(S3C_GINTSTS_EnumDone, hsotg->regs + S3C_GINTSTS);
+
+ s3c_hsotg_irq_enumdone(hsotg);
}
if (gintsts & S3C_GINTSTS_ConIDStsChng) {
if (daint_in & 1)
s3c_hsotg_epint(hsotg, ep, 1);
}
-
- writel(daint, hsotg->regs + S3C_DAINT);
- writel(gintsts & (S3C_GINTSTS_OEPInt | S3C_GINTSTS_IEPInt),
- hsotg->regs + S3C_GINTSTS);
}
if (gintsts & S3C_GINTSTS_USBRst) {
dev_dbg(hsotg->dev, "GNPTXSTS=%08x\n",
readl(hsotg->regs + S3C_GNPTXSTS));
+ writel(S3C_GINTSTS_USBRst, hsotg->regs + S3C_GINTSTS);
+
kill_all_requests(hsotg, &hsotg->eps[0], -ECONNRESET, true);
/* it seems after a reset we can end up with a situation
s3c_hsotg_init_fifo(hsotg);
s3c_hsotg_enqueue_setup(hsotg);
-
- writel(S3C_GINTSTS_USBRst, hsotg->regs + S3C_GINTSTS);
}
/* check both FIFOs */
s3c_hsotg_disable_gsint(hsotg, S3C_GINTSTS_NPTxFEmp);
s3c_hsotg_irq_fifoempty(hsotg, false);
-
- writel(S3C_GINTSTS_NPTxFEmp, hsotg->regs + S3C_GINTSTS);
}
if (gintsts & S3C_GINTSTS_PTxFEmp) {
s3c_hsotg_disable_gsint(hsotg, S3C_GINTSTS_PTxFEmp);
s3c_hsotg_irq_fifoempty(hsotg, true);
-
- writel(S3C_GINTSTS_PTxFEmp, hsotg->regs + S3C_GINTSTS);
}
if (gintsts & S3C_GINTSTS_RxFLvl) {
* set. */
s3c_hsotg_handle_rx(hsotg);
- writel(S3C_GINTSTS_RxFLvl, hsotg->regs + S3C_GINTSTS);
}
if (gintsts & S3C_GINTSTS_ModeMis) {
if (gintsts & S3C_GINTSTS_GOUTNakEff) {
dev_info(hsotg->dev, "GOUTNakEff triggered\n");
- s3c_hsotg_dump(hsotg);
-
writel(S3C_DCTL_CGOUTNak, hsotg->regs + S3C_DCTL);
- writel(S3C_GINTSTS_GOUTNakEff, hsotg->regs + S3C_GINTSTS);
+
+ s3c_hsotg_dump(hsotg);
}
if (gintsts & S3C_GINTSTS_GINNakEff) {
dev_info(hsotg->dev, "GINNakEff triggered\n");
- s3c_hsotg_dump(hsotg);
-
writel(S3C_DCTL_CGNPInNAK, hsotg->regs + S3C_DCTL);
- writel(S3C_GINTSTS_GINNakEff, hsotg->regs + S3C_GINTSTS);
+
+ s3c_hsotg_dump(hsotg);
}
/* if we've had fifo events, we should try and go around the
writel(1 << 18 | S3C_DCFG_DevSpd_HS, hsotg->regs + S3C_DCFG);
+ /* Clear any pending OTG interrupts */
+ writel(0xffffffff, hsotg->regs + S3C_GOTGINT);
+
+ /* Clear any pending interrupts */
+ writel(0xffffffff, hsotg->regs + S3C_GINTSTS);
+
writel(S3C_GINTSTS_DisconnInt | S3C_GINTSTS_SessReqInt |
S3C_GINTSTS_ConIDStsChng | S3C_GINTSTS_USBRst |
S3C_GINTSTS_EnumDone | S3C_GINTSTS_OTGInt |