net: dsa: mv88e6xxx: wait for AVB Busy bit
The AVB is not an indirect table using an Update bit, but a unit using a Busy bit. This means that we must ensure that this bit is cleared before setting it and wait until it gets cleared again after writing an operation. Reflect that. Signed-off-by: Vivien Didelot <vivien.didelot@gmail.com> Signed-off-by: David S. Miller <davem@davemloft.net>
This commit is contained in:
parent
19fb7f69da
commit
28ae1e9662
@ -11,6 +11,8 @@
|
||||
* Brandon Streiff <brandon.streiff@ni.com>
|
||||
*/
|
||||
|
||||
#include <linux/bitfield.h>
|
||||
|
||||
#include "global2.h"
|
||||
|
||||
/* Offset 0x16: AVB Command Register
|
||||
@ -27,17 +29,33 @@
|
||||
/* mv88e6xxx_g2_avb_read -- Read one or multiple 16-bit words.
|
||||
* The hardware supports snapshotting up to four contiguous registers.
|
||||
*/
|
||||
static int mv88e6xxx_g2_avb_wait(struct mv88e6xxx_chip *chip)
|
||||
{
|
||||
int bit = __bf_shf(MV88E6352_G2_AVB_CMD_BUSY);
|
||||
|
||||
return mv88e6xxx_g2_wait_bit(chip, MV88E6352_G2_AVB_CMD, bit, 0);
|
||||
}
|
||||
|
||||
static int mv88e6xxx_g2_avb_read(struct mv88e6xxx_chip *chip, u16 readop,
|
||||
u16 *data, int len)
|
||||
{
|
||||
int err;
|
||||
int i;
|
||||
|
||||
err = mv88e6xxx_g2_avb_wait(chip);
|
||||
if (err)
|
||||
return err;
|
||||
|
||||
/* Hardware can only snapshot four words. */
|
||||
if (len > 4)
|
||||
return -E2BIG;
|
||||
|
||||
err = mv88e6xxx_g2_update(chip, MV88E6352_G2_AVB_CMD, readop);
|
||||
err = mv88e6xxx_g2_write(chip, MV88E6352_G2_AVB_CMD,
|
||||
MV88E6352_G2_AVB_CMD_BUSY | readop);
|
||||
if (err)
|
||||
return err;
|
||||
|
||||
err = mv88e6xxx_g2_avb_wait(chip);
|
||||
if (err)
|
||||
return err;
|
||||
|
||||
@ -57,11 +75,18 @@ static int mv88e6xxx_g2_avb_write(struct mv88e6xxx_chip *chip, u16 writeop,
|
||||
{
|
||||
int err;
|
||||
|
||||
err = mv88e6xxx_g2_avb_wait(chip);
|
||||
if (err)
|
||||
return err;
|
||||
|
||||
err = mv88e6xxx_g2_write(chip, MV88E6352_G2_AVB_DATA, data);
|
||||
if (err)
|
||||
return err;
|
||||
|
||||
return mv88e6xxx_g2_update(chip, MV88E6352_G2_AVB_CMD, writeop);
|
||||
err = mv88e6xxx_g2_write(chip, MV88E6352_G2_AVB_CMD,
|
||||
MV88E6352_G2_AVB_CMD_BUSY | writeop);
|
||||
|
||||
return mv88e6xxx_g2_avb_wait(chip);
|
||||
}
|
||||
|
||||
static int mv88e6352_g2_avb_port_ptp_read(struct mv88e6xxx_chip *chip,
|
||||
|
Loading…
Reference in New Issue
Block a user