@@ -2108,8 +2108,47 @@ static int mlxsw_sp_port_lag_leave(struct mlxsw_sp_port *mlxsw_sp_port,
21082108 return 0 ;
21092109}
21102110
2111- static int mlxsw_sp_netdevice_port_event (struct net_device * dev ,
2112- unsigned long event , void * ptr )
2111+ static int mlxsw_sp_lag_dist_port_add (struct mlxsw_sp_port * mlxsw_sp_port ,
2112+ u16 lag_id )
2113+ {
2114+ struct mlxsw_sp * mlxsw_sp = mlxsw_sp_port -> mlxsw_sp ;
2115+ char sldr_pl [MLXSW_REG_SLDR_LEN ];
2116+
2117+ mlxsw_reg_sldr_lag_add_port_pack (sldr_pl , lag_id ,
2118+ mlxsw_sp_port -> local_port );
2119+ return mlxsw_reg_write (mlxsw_sp -> core , MLXSW_REG (sldr ), sldr_pl );
2120+ }
2121+
2122+ static int mlxsw_sp_lag_dist_port_remove (struct mlxsw_sp_port * mlxsw_sp_port ,
2123+ u16 lag_id )
2124+ {
2125+ struct mlxsw_sp * mlxsw_sp = mlxsw_sp_port -> mlxsw_sp ;
2126+ char sldr_pl [MLXSW_REG_SLDR_LEN ];
2127+
2128+ mlxsw_reg_sldr_lag_remove_port_pack (sldr_pl , lag_id ,
2129+ mlxsw_sp_port -> local_port );
2130+ return mlxsw_reg_write (mlxsw_sp -> core , MLXSW_REG (sldr ), sldr_pl );
2131+ }
2132+
2133+ static int mlxsw_sp_port_lag_tx_en_set (struct mlxsw_sp_port * mlxsw_sp_port ,
2134+ bool lag_tx_enabled )
2135+ {
2136+ if (lag_tx_enabled )
2137+ return mlxsw_sp_lag_dist_port_add (mlxsw_sp_port ,
2138+ mlxsw_sp_port -> lag_id );
2139+ else
2140+ return mlxsw_sp_lag_dist_port_remove (mlxsw_sp_port ,
2141+ mlxsw_sp_port -> lag_id );
2142+ }
2143+
2144+ static int mlxsw_sp_port_lag_changed (struct mlxsw_sp_port * mlxsw_sp_port ,
2145+ struct netdev_lag_lower_state_info * info )
2146+ {
2147+ return mlxsw_sp_port_lag_tx_en_set (mlxsw_sp_port , info -> tx_enabled );
2148+ }
2149+
2150+ static int mlxsw_sp_netdevice_port_upper_event (struct net_device * dev ,
2151+ unsigned long event , void * ptr )
21132152{
21142153 struct netdev_notifier_changeupper_info * info ;
21152154 struct mlxsw_sp_port * mlxsw_sp_port ;
@@ -2176,6 +2215,44 @@ static int mlxsw_sp_netdevice_port_event(struct net_device *dev,
21762215 return NOTIFY_DONE ;
21772216}
21782217
2218+ static int mlxsw_sp_netdevice_port_lower_event (struct net_device * dev ,
2219+ unsigned long event , void * ptr )
2220+ {
2221+ struct netdev_notifier_changelowerstate_info * info ;
2222+ struct mlxsw_sp_port * mlxsw_sp_port ;
2223+ int err ;
2224+
2225+ mlxsw_sp_port = netdev_priv (dev );
2226+ info = ptr ;
2227+
2228+ switch (event ) {
2229+ case NETDEV_CHANGELOWERSTATE :
2230+ if (netif_is_lag_port (dev ) && mlxsw_sp_port -> lagged ) {
2231+ err = mlxsw_sp_port_lag_changed (mlxsw_sp_port ,
2232+ info -> lower_state_info );
2233+ if (err )
2234+ netdev_err (dev , "Failed to reflect link aggregation lower state change\n" );
2235+ }
2236+ break ;
2237+ }
2238+
2239+ return NOTIFY_DONE ;
2240+ }
2241+
2242+ static int mlxsw_sp_netdevice_port_event (struct net_device * dev ,
2243+ unsigned long event , void * ptr )
2244+ {
2245+ switch (event ) {
2246+ case NETDEV_PRECHANGEUPPER :
2247+ case NETDEV_CHANGEUPPER :
2248+ return mlxsw_sp_netdevice_port_upper_event (dev , event , ptr );
2249+ case NETDEV_CHANGELOWERSTATE :
2250+ return mlxsw_sp_netdevice_port_lower_event (dev , event , ptr );
2251+ }
2252+
2253+ return NOTIFY_DONE ;
2254+ }
2255+
21792256static int mlxsw_sp_netdevice_lag_event (struct net_device * lag_dev ,
21802257 unsigned long event , void * ptr )
21812258{
0 commit comments