GFLADJ_30MHZ(val));
}
+#if defined(CONFIG_ARCH_VERSAL)
+static void dwc3_frame_length_adjustment(struct udevice *dev, struct dwc3 *dwc)
+{
+ u32 fladj, gfladj, reg;
+ bool refclk_fladj;
+
+ fladj = dev_read_u32_default(dev, "snps,quirk-frame-length-adjustment",
+ 0);
+ if (!fladj)
+ return;
+
+ /* Save the initial GFLADJ register value */
+ reg = readl(&dwc->g_fladj);
+ gfladj = reg;
+
+ refclk_fladj = dev_read_bool(dev, "snps,refclk_fladj");
+
+ if (refclk_fladj) {
+ if ((reg & GFLADJ_REFCLK_FLADJ) != (fladj &
+ GFLADJ_REFCLK_FLADJ)) {
+ reg &= ~GFLADJ_REFCLK_FLADJ;
+ reg |= (fladj & GFLADJ_REFCLK_FLADJ);
+ }
+ }
+
+ if ((reg & GFLADJ_30MHZ_MASK) != fladj) {
+ reg &= ~GFLADJ_30MHZ_MASK;
+ reg |= GFLADJ_30MHZ_REG_SEL | fladj;
+ }
+
+ /* Update GFLADJ if there is any change from initial value */
+ if (reg != gfladj)
+ writel(reg, &dwc->g_fladj);
+}
+#endif
+
#if CONFIG_IS_ENABLED(DM_USB)
static int xhci_dwc3_probe(struct udevice *dev)
{
dwc3_core_init(dwc3_reg);
+#if defined(CONFIG_ARCH_VERSAL)
+ /* Adjust Frame Length */
+ dwc3_frame_length_adjustment(dev, dwc3_reg);
+#endif
/* Set dwc3 usb2 phy config */
reg = readl(&dwc3_reg->g_usb2phycfg[0]);
/* Global Frame Length Adjustment Register */
#define GFLADJ_30MHZ_REG_SEL (1 << 7)
-#define GFLADJ_30MHZ(n) ((n) & 0x3f)
+#define GFLADJ_30MHZ(n) ((n) & GFLADJ_30MHZ_MASK)
+#define GFLADJ_30MHZ_MASK 0x3f
#define GFLADJ_30MHZ_DEFAULT 0x20
+#define GFLADJ_REFCLK_FLADJ (0x3fff << 8)
#ifdef CONFIG_USB_XHCI_DWC3
void dwc3_set_mode(struct dwc3 *dwc3_reg, u32 mode);