diff options
Diffstat (limited to 'net/hsr/hsr_device.c')
| -rw-r--r-- | net/hsr/hsr_device.c | 87 |
1 files changed, 39 insertions, 48 deletions
diff --git a/net/hsr/hsr_device.c b/net/hsr/hsr_device.c index a97bf326b231..f509b495451a 100644 --- a/net/hsr/hsr_device.c +++ b/net/hsr/hsr_device.c @@ -1,10 +1,6 @@ +// SPDX-License-Identifier: GPL-2.0 /* Copyright 2011-2014 Autronica Fire and Security AS * - * This program is free software; you can redistribute it and/or modify it - * under the terms of the GNU General Public License as published by the Free - * Software Foundation; either version 2 of the License, or (at your option) - * any later version. - * * Author(s): * 2011-2014 Arvid Brodin, arvid.brodin@alten.se * @@ -23,7 +19,6 @@ #include "hsr_main.h" #include "hsr_forward.h" - static bool is_admin_up(struct net_device *dev) { return dev && (dev->flags & IFF_UP); @@ -68,7 +63,7 @@ static bool hsr_check_carrier(struct hsr_port *master) rcu_read_lock(); hsr_for_each_port(master->hsr, port) - if ((port->type != HSR_PT_MASTER) && is_slave_up(port->dev)) { + if (port->type != HSR_PT_MASTER && is_slave_up(port->dev)) { has_carrier = true; break; } @@ -82,7 +77,6 @@ static bool hsr_check_carrier(struct hsr_port *master) return has_carrier; } - static void hsr_check_announce(struct net_device *hsr_dev, unsigned char old_operstate) { @@ -90,15 +84,14 @@ static void hsr_check_announce(struct net_device *hsr_dev, hsr = netdev_priv(hsr_dev); - if ((hsr_dev->operstate == IF_OPER_UP) - && (old_operstate != IF_OPER_UP)) { + if (hsr_dev->operstate == IF_OPER_UP && old_operstate != IF_OPER_UP) { /* Went up */ hsr->announce_count = 0; mod_timer(&hsr->announce_timer, jiffies + msecs_to_jiffies(HSR_ANNOUNCE_INTERVAL)); } - if ((hsr_dev->operstate != IF_OPER_UP) && (old_operstate == IF_OPER_UP)) + if (hsr_dev->operstate != IF_OPER_UP && old_operstate == IF_OPER_UP) /* Went down */ del_timer(&hsr->announce_timer); } @@ -136,7 +129,6 @@ int hsr_get_max_mtu(struct hsr_priv *hsr) return mtu_max - HSR_HLEN; } - static int hsr_dev_change_mtu(struct net_device *dev, int new_mtu) { struct hsr_priv *hsr; @@ -191,14 +183,12 @@ static int hsr_dev_open(struct net_device *dev) return 0; } - static int hsr_dev_close(struct net_device *dev) { /* Nothing to do here. */ return 0; } - static netdev_features_t hsr_features_recompute(struct hsr_priv *hsr, netdev_features_t features) { @@ -231,7 +221,6 @@ static netdev_features_t hsr_fix_features(struct net_device *dev, return hsr_features_recompute(hsr, features); } - static int hsr_dev_xmit(struct sk_buff *skb, struct net_device *dev) { struct hsr_priv *hsr = netdev_priv(dev); @@ -240,18 +229,16 @@ static int hsr_dev_xmit(struct sk_buff *skb, struct net_device *dev) master = hsr_port_get_hsr(hsr, HSR_PT_MASTER); skb->dev = master->dev; hsr_forward_skb(skb, master); - return NETDEV_TX_OK; } - static const struct header_ops hsr_header_ops = { .create = eth_header, .parse = eth_header_parse, }; static void send_hsr_supervision_frame(struct hsr_port *master, - u8 type, u8 hsrVer) + u8 type, u8 hsr_ver) { struct sk_buff *skb; int hlen, tlen; @@ -262,39 +249,38 @@ static void send_hsr_supervision_frame(struct hsr_port *master, hlen = LL_RESERVED_SPACE(master->dev); tlen = master->dev->needed_tailroom; - skb = dev_alloc_skb( - sizeof(struct hsr_tag) + - sizeof(struct hsr_sup_tag) + - sizeof(struct hsr_sup_payload) + hlen + tlen); + skb = dev_alloc_skb(sizeof(struct hsr_tag) + + sizeof(struct hsr_sup_tag) + + sizeof(struct hsr_sup_payload) + hlen + tlen); - if (skb == NULL) + if (!skb) return; skb_reserve(skb, hlen); skb->dev = master->dev; - skb->protocol = htons(hsrVer ? ETH_P_HSR : ETH_P_PRP); + skb->protocol = htons(hsr_ver ? ETH_P_HSR : ETH_P_PRP); skb->priority = TC_PRIO_CONTROL; - if (dev_hard_header(skb, skb->dev, (hsrVer ? ETH_P_HSR : ETH_P_PRP), + if (dev_hard_header(skb, skb->dev, (hsr_ver ? ETH_P_HSR : ETH_P_PRP), master->hsr->sup_multicast_addr, skb->dev->dev_addr, skb->len) <= 0) goto out; skb_reset_mac_header(skb); - if (hsrVer > 0) { + if (hsr_ver > 0) { hsr_tag = skb_put(skb, sizeof(struct hsr_tag)); hsr_tag->encap_proto = htons(ETH_P_PRP); set_hsr_tag_LSDU_size(hsr_tag, HSR_V1_SUP_LSDUSIZE); } hsr_stag = skb_put(skb, sizeof(struct hsr_sup_tag)); - set_hsr_stag_path(hsr_stag, (hsrVer ? 0x0 : 0xf)); - set_hsr_stag_HSR_Ver(hsr_stag, hsrVer); + set_hsr_stag_path(hsr_stag, (hsr_ver ? 0x0 : 0xf)); + set_hsr_stag_HSR_ver(hsr_stag, hsr_ver); /* From HSRv1 on we have separate supervision sequence numbers. */ spin_lock_irqsave(&master->hsr->seqnr_lock, irqflags); - if (hsrVer > 0) { + if (hsr_ver > 0) { hsr_stag->sequence_nr = htons(master->hsr->sup_sequence_nr); hsr_tag->sequence_nr = htons(master->hsr->sequence_nr); master->hsr->sup_sequence_nr++; @@ -305,13 +291,14 @@ static void send_hsr_supervision_frame(struct hsr_port *master, } spin_unlock_irqrestore(&master->hsr->seqnr_lock, irqflags); - hsr_stag->HSR_TLV_Type = type; + hsr_stag->HSR_TLV_type = type; /* TODO: Why 12 in HSRv0? */ - hsr_stag->HSR_TLV_Length = hsrVer ? sizeof(struct hsr_sup_payload) : 12; + hsr_stag->HSR_TLV_length = + hsr_ver ? sizeof(struct hsr_sup_payload) : 12; /* Payload: MacAddressA */ hsr_sp = skb_put(skb, sizeof(struct hsr_sup_payload)); - ether_addr_copy(hsr_sp->MacAddressA, master->dev->dev_addr); + ether_addr_copy(hsr_sp->macaddress_A, master->dev->dev_addr); if (skb_put_padto(skb, ETH_ZLEN + HSR_HLEN)) return; @@ -324,7 +311,6 @@ out: kfree_skb(skb); } - /* Announce (supervision frame) timer function */ static void hsr_announce(struct timer_list *t) @@ -338,15 +324,15 @@ static void hsr_announce(struct timer_list *t) rcu_read_lock(); master = hsr_port_get_hsr(hsr, HSR_PT_MASTER); - if (hsr->announce_count < 3 && hsr->protVersion == 0) { + if (hsr->announce_count < 3 && hsr->prot_version == 0) { send_hsr_supervision_frame(master, HSR_TLV_ANNOUNCE, - hsr->protVersion); + hsr->prot_version); hsr->announce_count++; interval = msecs_to_jiffies(HSR_ANNOUNCE_INTERVAL); } else { send_hsr_supervision_frame(master, HSR_TLV_LIFE_CHECK, - hsr->protVersion); + hsr->prot_version); interval = msecs_to_jiffies(HSR_LIFE_CHECK_INTERVAL); } @@ -357,26 +343,28 @@ static void hsr_announce(struct timer_list *t) rcu_read_unlock(); } - -/* According to comments in the declaration of struct net_device, this function - * is "Called from unregister, can be used to call free_netdev". Ok then... +/* This has to be called after all the readers are gone. + * Otherwise we would have to check the return value of + * hsr_port_get_hsr(). */ static void hsr_dev_destroy(struct net_device *hsr_dev) { struct hsr_priv *hsr; struct hsr_port *port; + struct hsr_port *tmp; hsr = netdev_priv(hsr_dev); - rtnl_lock(); - hsr_for_each_port(hsr, port) + hsr_debugfs_term(hsr); + + list_for_each_entry_safe(port, tmp, &hsr->ports, port_list) hsr_del_port(port); - rtnl_unlock(); del_timer_sync(&hsr->prune_timer); del_timer_sync(&hsr->announce_timer); - synchronize_rcu(); + hsr_del_self_node(&hsr->self_node_db); + hsr_del_nodes(&hsr->node_db); } static const struct net_device_ops hsr_device_ops = { @@ -385,6 +373,7 @@ static const struct net_device_ops hsr_device_ops = { .ndo_stop = hsr_dev_close, .ndo_start_xmit = hsr_dev_xmit, .ndo_fix_features = hsr_fix_features, + .ndo_uninit = hsr_dev_destroy, }; static struct device_type hsr_type = { @@ -403,7 +392,6 @@ void hsr_dev_setup(struct net_device *dev) dev->priv_flags |= IFF_NO_QUEUE; dev->needs_free_netdev = true; - dev->priv_destructor = hsr_dev_destroy; dev->hw_features = NETIF_F_SG | NETIF_F_FRAGLIST | NETIF_F_HIGHDMA | NETIF_F_GSO_MASK | NETIF_F_HW_CSUM | @@ -423,7 +411,6 @@ void hsr_dev_setup(struct net_device *dev) dev->features |= NETIF_F_NETNS_LOCAL; } - /* Return true if dev is a HSR master; return false otherwise. */ inline bool is_hsr_master(struct net_device *dev) @@ -441,6 +428,7 @@ int hsr_dev_finalize(struct net_device *hsr_dev, struct net_device *slave[2], { struct hsr_priv *hsr; struct hsr_port *port; + struct hsr_port *tmp; int res; hsr = netdev_priv(hsr_dev); @@ -467,7 +455,7 @@ int hsr_dev_finalize(struct net_device *hsr_dev, struct net_device *slave[2], ether_addr_copy(hsr->sup_multicast_addr, def_multicast_addr); hsr->sup_multicast_addr[ETH_ALEN - 1] = multicast_spec; - hsr->protVersion = protocol_version; + hsr->prot_version = protocol_version; /* FIXME: should I modify the value of these? * @@ -498,14 +486,17 @@ int hsr_dev_finalize(struct net_device *hsr_dev, struct net_device *slave[2], goto fail; mod_timer(&hsr->prune_timer, jiffies + msecs_to_jiffies(PRUNE_PERIOD)); + res = hsr_debugfs_init(hsr, hsr_dev); + if (res) + goto fail; return 0; fail: - hsr_for_each_port(hsr, port) + list_for_each_entry_safe(port, tmp, &hsr->ports, port_list) hsr_del_port(port); err_add_port: - hsr_del_node(&hsr->self_node_db); + hsr_del_self_node(&hsr->self_node_db); return res; } |
