Hello, I feel like intruding posting to this list, let me know if
that is the case.

This post:

https://marc.info/?l=openbsd-arm&m=159333005826561&w=2

made me try again OpenBSD on an H3 board, an Orange Pi One unusable with
random faults at boot.

The firs thing I noticed was that PLL_CPUX wasn't stabilized although
LOCK was read as set. Gating the PLL before setting the factors
solved the problem. I added a delay(1) after switching the CPUX
clock source, the datasheet advises of a delay of at least 8 cycles
of the current clock. No more random faults at boot.
==================================================================
--- /usr/src/sys/dev/fdt/sxiccmu.c.orig Wed Jul  8 21:23:35 2020
+++ /usr/src/sys/dev/fdt/sxiccmu.c      Fri Jul 10 21:35:49 2020
@@ -1158,6 +1158,7 @@
 
 /* Allwinner H3/H5 */
 #define H3_PLL_CPUX_CTRL_REG           0x0000
+#define H3_PLL_CPUX_ENABLE             (1 << 31)
 #define H3_PLL_CPUX_LOCK               (1 << 28)
 #define H3_PLL_CPUX_OUT_EXT_DIVP(x)    (((x) >> 16) & 0x3)
 #define H3_PLL_CPUX_OUT_EXT_DIVP_MASK  (0x3 << 16)
@@ -1644,7 +1645,12 @@
                while (n >= 1 && (24000000 * n * k) > freq)
                        n--;
 
+               /* Gate the PLL first */
                reg = SXIREAD4(sc, H3_PLL_CPUX_CTRL_REG);
+               reg &= ~H3_PLL_CPUX_ENABLE;
+               SXIWRITE4(sc, H3_PLL_CPUX_CTRL_REG, reg);
+
+               /* Set factors and external divider. */
                reg &= ~H3_PLL_CPUX_OUT_EXT_DIVP_MASK;
                reg &= ~H3_PLL_CPUX_FACTOR_N_MASK;
                reg &= ~H3_PLL_CPUX_FACTOR_K_MASK;
@@ -1653,6 +1659,10 @@
                reg |= ((k - 1) << H3_PLL_CPUX_FACTOR_K_SHIFT);
                SXIWRITE4(sc, H3_PLL_CPUX_CTRL_REG, reg);
 
+               /* Ungate the PLL */
+               reg |= H3_PLL_CPUX_ENABLE;
+               SXIWRITE4(sc, H3_PLL_CPUX_CTRL_REG, reg);
+
                /* Wait for PLL to lock. */
                while ((SXIREAD4(sc, H3_PLL_CPUX_CTRL_REG) &
                    H3_PLL_CPUX_LOCK) == 0)
@@ -1665,6 +1675,8 @@
                reg &= ~H3_CPUX_CLK_SRC_SEL;
                reg |= H3_CPUX_CLK_SRC_SEL_OSC24M;
                SXIWRITE4(sc, H3_CPUX_AXI_CFG_REG, reg);
+               /* Must wait at least 8 cycles of the current clock. */
+               delay(1);
 
                error = sxiccmu_h3_set_frequency(sc, H3_CLK_PLL_CPUX, freq);
 
@@ -1673,6 +1685,7 @@
                reg &= ~H3_CPUX_CLK_SRC_SEL;
                reg |= H3_CPUX_CLK_SRC_SEL_PLL_CPUX;
                SXIWRITE4(sc, H3_CPUX_AXI_CFG_REG, reg);
+               delay(1);
                return error;
        case H3_CLK_MMC0:
        case H3_CLK_MMC1:
==================================================================

Next thing: DVFS failed, low voltage for the frequency and randoms
traps in thermal_sensor_update.

In src/sys/arch/arm/arm/cpu.c, cpu_opp_dotask() tries to set the
cpux regulator's voltage to the preferred value (first element in
the triplet of opp-microvolt) of the operating point in the opp_table.
The problem is that this table doesn't correspond with the states
of the regulator on the board, a SY8113B that will output just 1,1v
or 1,3v.

There are two options, patch the dts to match the regulator or change
the code.  One approach is to set opp_microvolt in cpu_opp_init()
to the most appropriate of the supported volts of the cpu supply that are
between min and max. Another is to change regulator_set_voltage() in
sys/dev/ofw/ofw_regulator.c to admit 3 parameters: desired voltage, min
and max and make the selection there. I prefer just to adjust the dtb.

[...]
        opp_table0 {
                compatible = "operating-points-v2";
                opp-shared;
                phandle = <0x29>;

                opp-648000000 {
                        opp-hz = <0x00 0x269fb200>;
                        opp-microvolt = <0x10c8e0 0x10c8e0 0x13d620>;
                        clock-latency-ns = <0x3b9b0>;
                };

                opp-816000000 {
                        opp-hz = <0x00 0x30a32c00>;
                        opp-microvolt = <0x10c8e0 0x10c8e0 0x13d620>;
                        clock-latency-ns = <0x3b9b0>;
                };

                opp-1008000000 {
                        opp-hz = <0x00 0x3c14dc00>;
                        opp-microvolt = <0x13d620 0x13d620 0x13d620>;
                        clock-latency-ns = <0x3b9b0>;
                };
        };
[...]

The board seams to be stable now.

Regards,
adr.

Reply via email to