return ret;
 }
 
-static int mv88e6xxx_set_addr_direct(struct dsa_switch *ds, u8 *addr)
-{
-       struct mv88e6xxx_chip *chip = ds_to_priv(ds);
-       int err;
-
-       err = mv88e6xxx_reg_write(chip, REG_GLOBAL, GLOBAL_MAC_01,
-                                 (addr[0] << 8) | addr[1]);
-       if (err)
-               return err;
-
-       err = mv88e6xxx_reg_write(chip, REG_GLOBAL, GLOBAL_MAC_23,
-                                 (addr[2] << 8) | addr[3]);
-       if (err)
-               return err;
-
-       return mv88e6xxx_reg_write(chip, REG_GLOBAL, GLOBAL_MAC_45,
-                                  (addr[4] << 8) | addr[5]);
-}
-
-static int mv88e6xxx_set_addr_indirect(struct dsa_switch *ds, u8 *addr)
-{
-       struct mv88e6xxx_chip *chip = ds_to_priv(ds);
-       int ret;
-       int i;
-
-       for (i = 0; i < 6; i++) {
-               int j;
-
-               /* Write the MAC address byte. */
-               ret = mv88e6xxx_reg_write(chip, REG_GLOBAL2, GLOBAL2_SWITCH_MAC,
-                                         GLOBAL2_SWITCH_MAC_BUSY |
-                                         (i << 8) | addr[i]);
-               if (ret)
-                       return ret;
-
-               /* Wait for the write to complete. */
-               for (j = 0; j < 16; j++) {
-                       ret = mv88e6xxx_reg_read(chip, REG_GLOBAL2,
-                                                GLOBAL2_SWITCH_MAC);
-                       if (ret < 0)
-                               return ret;
-
-                       if ((ret & GLOBAL2_SWITCH_MAC_BUSY) == 0)
-                               break;
-               }
-               if (j == 16)
-                       return -ETIMEDOUT;
-       }
-
-       return 0;
-}
-
-static int mv88e6xxx_set_addr(struct dsa_switch *ds, u8 *addr)
-{
-       struct mv88e6xxx_chip *chip = ds_to_priv(ds);
-
-       if (mv88e6xxx_has(chip, MV88E6XXX_FLAG_SWITCH_MAC))
-               return mv88e6xxx_set_addr_indirect(ds, addr);
-       else
-               return mv88e6xxx_set_addr_direct(ds, addr);
-}
-
 static int mv88e6xxx_mdio_read_direct(struct mv88e6xxx_chip *chip,
                                      int addr, int regnum)
 {
        return 0;
 }
 
+static int mv88e6xxx_g1_set_switch_mac(struct mv88e6xxx_chip *chip, u8 *addr)
+{
+       int err;
+
+       err = mv88e6xxx_write(chip, REG_GLOBAL, GLOBAL_MAC_01,
+                             (addr[0] << 8) | addr[1]);
+       if (err)
+               return err;
+
+       err = mv88e6xxx_write(chip, REG_GLOBAL, GLOBAL_MAC_23,
+                             (addr[2] << 8) | addr[3]);
+       if (err)
+               return err;
+
+       return mv88e6xxx_write(chip, REG_GLOBAL, GLOBAL_MAC_45,
+                              (addr[4] << 8) | addr[5]);
+}
+
 static int mv88e6xxx_g1_setup(struct mv88e6xxx_chip *chip)
 {
        struct dsa_switch *ds = chip->ds;
        return 0;
 }
 
+/* Indirect write to the Switch MAC/WoL/WoF register */
+static int mv88e6xxx_g2_switch_mac_write(struct mv88e6xxx_chip *chip,
+                                        unsigned int pointer, u8 data)
+{
+       u16 val = (pointer << 8) | data;
+
+       return mv88e6xxx_update(chip, REG_GLOBAL2, GLOBAL2_SWITCH_MAC, val);
+}
+
+static int mv88e6xxx_g2_set_switch_mac(struct mv88e6xxx_chip *chip, u8 *addr)
+{
+       int i, err;
+
+       for (i = 0; i < 6; i++) {
+               err = mv88e6xxx_g2_switch_mac_write(chip, i, addr[i]);
+               if (err)
+                       break;
+       }
+
+       return err;
+}
+
 static int mv88e6xxx_g2_setup(struct mv88e6xxx_chip *chip)
 {
        u16 reg;
        return err;
 }
 
+static int mv88e6xxx_set_addr(struct dsa_switch *ds, u8 *addr)
+{
+       struct mv88e6xxx_chip *chip = ds_to_priv(ds);
+       int err;
+
+       mutex_lock(&chip->reg_lock);
+
+       /* Has an indirect Switch MAC/WoL/WoF register in Global 2? */
+       if (mv88e6xxx_has(chip, MV88E6XXX_FLAG_G2_SWITCH_MAC))
+               err = mv88e6xxx_g2_set_switch_mac(chip, addr);
+       else
+               err = mv88e6xxx_g1_set_switch_mac(chip, addr);
+
+       mutex_unlock(&chip->reg_lock);
+
+       return err;
+}
+
 static int mv88e6xxx_mdio_page_read(struct dsa_switch *ds, int port, int page,
                                    int reg)
 {
 
 #define GLOBAL2_PVT_ADDR       0x0b
 #define GLOBAL2_PVT_DATA       0x0c
 #define GLOBAL2_SWITCH_MAC     0x0d
-#define GLOBAL2_SWITCH_MAC_BUSY BIT(15)
 #define GLOBAL2_ATU_STATS      0x0e
 #define GLOBAL2_PRIO_OVERRIDE  0x0f
 #define GLOBAL2_PRIO_OVERRIDE_FORCE_SNOOP      BIT(7)
        MV88E6XXX_CAP_GLOBAL2,
        MV88E6XXX_CAP_G2_MGMT_EN_2X,    /* (0x02) MGMT Enable Register 2x */
        MV88E6XXX_CAP_G2_MGMT_EN_0X,    /* (0x03) MGMT Enable Register 0x */
+       MV88E6XXX_CAP_G2_SWITCH_MAC,    /* (0x0d) Switch MAC/WoL/WoF */
 
        /* Multi-chip Addressing Mode.
         * Some chips require an indirect SMI access when their SMI device
         */
        MV88E6XXX_CAP_STU,
 
-       /* Switch MAC/WoL/WoF register.
-        * This requires an indirect access to set the switch MAC address
-        * through GLOBAL2_SWITCH_MAC, otherwise GLOBAL_MAC_01, GLOBAL_MAC_23,
-        * and GLOBAL_MAC_45 are used with a direct access.
-        */
-       MV88E6XXX_CAP_SWITCH_MAC_WOL_WOF,
-
        /* Internal temperature sensor.
         * Available from any enabled port's PHY register 26, page 6.
         */
 #define MV88E6XXX_FLAG_GLOBAL2         BIT(MV88E6XXX_CAP_GLOBAL2)
 #define MV88E6XXX_FLAG_G2_MGMT_EN_2X   BIT(MV88E6XXX_CAP_G2_MGMT_EN_2X)
 #define MV88E6XXX_FLAG_G2_MGMT_EN_0X   BIT(MV88E6XXX_CAP_G2_MGMT_EN_0X)
+#define MV88E6XXX_FLAG_G2_SWITCH_MAC   BIT(MV88E6XXX_CAP_G2_SWITCH_MAC)
 #define MV88E6XXX_FLAG_MULTI_CHIP      BIT(MV88E6XXX_CAP_MULTI_CHIP)
 #define MV88E6XXX_FLAG_PPU             BIT(MV88E6XXX_CAP_PPU)
 #define MV88E6XXX_FLAG_PPU_ACTIVE      BIT(MV88E6XXX_CAP_PPU_ACTIVE)
 #define MV88E6XXX_FLAG_SMI_PHY         BIT(MV88E6XXX_CAP_SMI_PHY)
 #define MV88E6XXX_FLAG_STU             BIT(MV88E6XXX_CAP_STU)
-#define MV88E6XXX_FLAG_SWITCH_MAC      BIT(MV88E6XXX_CAP_SWITCH_MAC_WOL_WOF)
 #define MV88E6XXX_FLAG_TEMP            BIT(MV88E6XXX_CAP_TEMP)
 #define MV88E6XXX_FLAG_TEMP_LIMIT      BIT(MV88E6XXX_CAP_TEMP_LIMIT)
 #define MV88E6XXX_FLAG_VTU             BIT(MV88E6XXX_CAP_VTU)
        (MV88E6XXX_FLAG_GLOBAL2 |       \
         MV88E6XXX_FLAG_G2_MGMT_EN_2X | \
         MV88E6XXX_FLAG_G2_MGMT_EN_0X | \
+        MV88E6XXX_FLAG_G2_SWITCH_MAC | \
         MV88E6XXX_FLAG_MULTI_CHIP |    \
         MV88E6XXX_FLAG_STU |           \
-        MV88E6XXX_FLAG_SWITCH_MAC |    \
         MV88E6XXX_FLAG_TEMP |          \
         MV88E6XXX_FLAG_VTU)
 
         MV88E6XXX_FLAG_GLOBAL2 |       \
         MV88E6XXX_FLAG_G2_MGMT_EN_2X | \
         MV88E6XXX_FLAG_G2_MGMT_EN_0X | \
+        MV88E6XXX_FLAG_G2_SWITCH_MAC | \
         MV88E6XXX_FLAG_MULTI_CHIP |    \
         MV88E6XXX_FLAG_PPU_ACTIVE |    \
         MV88E6XXX_FLAG_SMI_PHY |       \
-        MV88E6XXX_FLAG_SWITCH_MAC |    \
         MV88E6XXX_FLAG_TEMP |          \
         MV88E6XXX_FLAG_TEMP_LIMIT |    \
         MV88E6XXX_FLAG_VTU)
        (MV88E6XXX_FLAG_GLOBAL2 |       \
         MV88E6XXX_FLAG_G2_MGMT_EN_2X | \
         MV88E6XXX_FLAG_G2_MGMT_EN_0X | \
+        MV88E6XXX_FLAG_G2_SWITCH_MAC | \
         MV88E6XXX_FLAG_MULTI_CHIP |    \
         MV88E6XXX_FLAG_PPU_ACTIVE |    \
         MV88E6XXX_FLAG_SMI_PHY |       \
         MV88E6XXX_FLAG_STU |           \
-        MV88E6XXX_FLAG_SWITCH_MAC |    \
         MV88E6XXX_FLAG_TEMP |          \
         MV88E6XXX_FLAG_VTU)
 
         MV88E6XXX_FLAG_GLOBAL2 |       \
         MV88E6XXX_FLAG_G2_MGMT_EN_2X | \
         MV88E6XXX_FLAG_G2_MGMT_EN_0X | \
+        MV88E6XXX_FLAG_G2_SWITCH_MAC | \
         MV88E6XXX_FLAG_MULTI_CHIP |    \
         MV88E6XXX_FLAG_PPU_ACTIVE |    \
         MV88E6XXX_FLAG_SMI_PHY |       \
         MV88E6XXX_FLAG_STU |           \
-        MV88E6XXX_FLAG_SWITCH_MAC |    \
         MV88E6XXX_FLAG_TEMP |          \
         MV88E6XXX_FLAG_TEMP_LIMIT |    \
         MV88E6XXX_FLAG_VTU)