• Vladimir Oltean's avatar
    net: dsa: let drivers state that they need VLAN filtering while standalone · 58adf9dc
    Vladimir Oltean authored
    As explained in commit e358bef7 ("net: dsa: Give drivers the chance
    to veto certain upper devices"), the hellcreek driver uses some tricks
    to comply with the network stack expectations: it enforces port
    separation in standalone mode using VLANs. For untagged traffic,
    bridging between ports is prevented by using different PVIDs, and for
    VLAN-tagged traffic, it never accepts 8021q uppers with the same VID on
    two ports, so packets with one VLAN cannot leak from one port to another.
    
    That is almost fine*, and has worked because hellcreek relied on an
    implicit behavior of the DSA core that was changed by the previous
    patch: the standalone ports declare the 'rx-vlan-filter' feature as 'on
    [fixed]'. Since most of the DSA drivers are actually VLAN-unaware in
    standalone mode, that feature was actually incorrectly reflecting the
    hardware/driver state, so there was a desire to fix it. This leaves the
    hellcreek driver in a situation where it has to explicitly request this
    behavior from the DSA framework.
    
    We configure the ports as follows:
    
    - Standalone: 'rx-vlan-filter' is on. An 8021q upper on top of a
      standalone hellcreek port will go through dsa_slave_vlan_rx_add_vid
      and will add a VLAN to the hardware tables, giving the driver the
      opportunity to refuse it through .port_prechangeupper.
    
    - Bridged with vlan_filtering=0: 'rx-vlan-filter' is off. An 8021q upper
      on top of a bridged hellcreek port will not go through
      dsa_slave_vlan_rx_add_vid, because there will not be any attempt to
      offload this VLAN. The driver already disables VLAN awareness, so that
      upper should receive the traffic it needs.
    
    - Bridged with vlan_filtering=1: 'rx-vlan-filter' is on. An 8021q upper
      on top of a bridged hellcreek port will call dsa_slave_vlan_rx_add_vid,
      and can again be vetoed through .port_prechangeupper.
    
    *It is not actually completely fine, because if I follow through
    correctly, we can have the following situation:
    
    ip link add br0 type bridge vlan_filtering 0
    ip link set lan0 master br0 # lan0 now becomes VLAN-unaware
    ip link set lan0 nomaster # lan0 fails to become VLAN-aware again, therefore breaking isolation
    
    This patch fixes that corner case by extending the DSA core logic, based
    on this requested attribute, to change the VLAN awareness state of the
    switch (port) when it leaves the bridge.
    Signed-off-by: default avatarVladimir Oltean <vladimir.oltean@nxp.com>
    Reviewed-by: default avatarFlorian Fainelli <f.fainelli@gmail.com>
    Acked-by: Kurt Kanzenbach's avatarKurt Kanzenbach <kurt@linutronix.de>
    Signed-off-by: default avatarDavid S. Miller <davem@davemloft.net>
    58adf9dc
slave.c 65.8 KB