1 /* SPDX-License-Identifier: GPL-2.0-or-later */ 2 /* 3 * Copyright (c) 2026 David Yang 4 */ 5 6 #ifndef _YT_SMI_H 7 #define _YT_SMI_H 8 9 #include <linux/types.h> 10 #include <linux/wordpart.h> 11 12 struct yt921x_priv; 13 14 int yt921x_reg_read(struct yt921x_priv *priv, u32 reg, u32 *valp); 15 int yt921x_reg_write(struct yt921x_priv *priv, u32 reg, u32 val); 16 int yt921x_reg_wait(struct yt921x_priv *priv, u32 reg, u32 mask, u32 *valp); 17 int yt921x_reg_update_bits(struct yt921x_priv *priv, u32 reg, u32 mask, 18 u32 val); 19 20 static inline int 21 yt921x_reg_set_bits(struct yt921x_priv *priv, u32 reg, u32 mask) 22 { 23 return yt921x_reg_update_bits(priv, reg, 0, mask); 24 } 25 26 static inline int 27 yt921x_reg_clear_bits(struct yt921x_priv *priv, u32 reg, u32 mask) 28 { 29 return yt921x_reg_update_bits(priv, reg, mask, 0); 30 } 31 32 static inline int 33 yt921x_reg_toggle_bits(struct yt921x_priv *priv, u32 reg, u32 mask, bool set) 34 { 35 return yt921x_reg_update_bits(priv, reg, mask, !set ? 0 : mask); 36 } 37 38 /* Some multi-word registers, like VLANn_CTRL, should be treated as a single 39 * long register. More specifically, writes to parts of its words won't become 40 * visible, until the last word is written. 41 * 42 * Here we require full read and write operations over these registers to 43 * eliminate potential issues, although partial reads/writes are also possible. 44 */ 45 46 static inline void update_ctrls_unaligned(u32 *lo, u32 *hi, u64 mask, u64 val) 47 { 48 *lo &= ~lower_32_bits(mask); 49 *hi &= ~upper_32_bits(mask); 50 *lo |= lower_32_bits(val); 51 *hi |= upper_32_bits(val); 52 } 53 54 int yt921x_reg64_write(struct yt921x_priv *priv, u32 reg, const u32 *vals); 55 int yt921x_reg64_update_bits(struct yt921x_priv *priv, u32 reg, 56 const u32 *masks, const u32 *vals); 57 int yt921x_reg64_clear_bits(struct yt921x_priv *priv, u32 reg, 58 const u32 *masks); 59 int yt921x_reg96_write(struct yt921x_priv *priv, u32 reg, const u32 *vals); 60 61 #endif 62