Message ID | 20220105132141.2648876-6-vladimir.oltean@nxp.com (mailing list archive) |
---|---|
State | Accepted |
Delegated to: | Netdev Maintainers |
Headers | show |
Series | Cleanup to main DSA structures | expand |
On 1/5/22 5:21 AM, Vladimir Oltean wrote: > Currently, num_ports is declared as size_t, which is defined as > __kernel_ulong_t, therefore it occupies 8 bytes of memory. > > Even switches with port numbers in the range of tens are exotic, so > there is no need for this amount of storage. > > Additionally, because the max_num_bridges member right above it is also > 4 bytes, it means the compiler needs to add padding between the last 2 > fields. By reducing the size, we don't need that padding and can reduce > the struct size. > > Before: > > pahole -C dsa_switch net/dsa/slave.o > struct dsa_switch { > struct device * dev; /* 0 8 */ > struct dsa_switch_tree * dst; /* 8 8 */ > unsigned int index; /* 16 4 */ > u32 setup:1; /* 20: 0 4 */ > u32 vlan_filtering_is_global:1; /* 20: 1 4 */ > u32 needs_standalone_vlan_filtering:1; /* 20: 2 4 */ > u32 configure_vlan_while_not_filtering:1; /* 20: 3 4 */ > u32 untag_bridge_pvid:1; /* 20: 4 4 */ > u32 assisted_learning_on_cpu_port:1; /* 20: 5 4 */ > u32 vlan_filtering:1; /* 20: 6 4 */ > u32 pcs_poll:1; /* 20: 7 4 */ > u32 mtu_enforcement_ingress:1; /* 20: 8 4 */ > > /* XXX 23 bits hole, try to pack */ > > struct notifier_block nb; /* 24 24 */ > > /* XXX last struct has 4 bytes of padding */ > > void * priv; /* 48 8 */ > void * tagger_data; /* 56 8 */ > /* --- cacheline 1 boundary (64 bytes) --- */ > struct dsa_chip_data * cd; /* 64 8 */ > const struct dsa_switch_ops * ops; /* 72 8 */ > u32 phys_mii_mask; /* 80 4 */ > > /* XXX 4 bytes hole, try to pack */ > > struct mii_bus * slave_mii_bus; /* 88 8 */ > unsigned int ageing_time_min; /* 96 4 */ > unsigned int ageing_time_max; /* 100 4 */ > struct dsa_8021q_context * tag_8021q_ctx; /* 104 8 */ > struct devlink * devlink; /* 112 8 */ > unsigned int num_tx_queues; /* 120 4 */ > unsigned int num_lag_ids; /* 124 4 */ > /* --- cacheline 2 boundary (128 bytes) --- */ > unsigned int max_num_bridges; /* 128 4 */ > > /* XXX 4 bytes hole, try to pack */ > > size_t num_ports; /* 136 8 */ > > /* size: 144, cachelines: 3, members: 27 */ > /* sum members: 132, holes: 2, sum holes: 8 */ > /* sum bitfield members: 9 bits, bit holes: 1, sum bit holes: 23 bits */ > /* paddings: 1, sum paddings: 4 */ > /* last cacheline: 16 bytes */ > }; > > After: > > pahole -C dsa_switch net/dsa/slave.o > struct dsa_switch { > struct device * dev; /* 0 8 */ > struct dsa_switch_tree * dst; /* 8 8 */ > unsigned int index; /* 16 4 */ > u32 setup:1; /* 20: 0 4 */ > u32 vlan_filtering_is_global:1; /* 20: 1 4 */ > u32 needs_standalone_vlan_filtering:1; /* 20: 2 4 */ > u32 configure_vlan_while_not_filtering:1; /* 20: 3 4 */ > u32 untag_bridge_pvid:1; /* 20: 4 4 */ > u32 assisted_learning_on_cpu_port:1; /* 20: 5 4 */ > u32 vlan_filtering:1; /* 20: 6 4 */ > u32 pcs_poll:1; /* 20: 7 4 */ > u32 mtu_enforcement_ingress:1; /* 20: 8 4 */ > > /* XXX 23 bits hole, try to pack */ > > struct notifier_block nb; /* 24 24 */ > > /* XXX last struct has 4 bytes of padding */ > > void * priv; /* 48 8 */ > void * tagger_data; /* 56 8 */ > /* --- cacheline 1 boundary (64 bytes) --- */ > struct dsa_chip_data * cd; /* 64 8 */ > const struct dsa_switch_ops * ops; /* 72 8 */ > u32 phys_mii_mask; /* 80 4 */ > > /* XXX 4 bytes hole, try to pack */ > > struct mii_bus * slave_mii_bus; /* 88 8 */ > unsigned int ageing_time_min; /* 96 4 */ > unsigned int ageing_time_max; /* 100 4 */ > struct dsa_8021q_context * tag_8021q_ctx; /* 104 8 */ > struct devlink * devlink; /* 112 8 */ > unsigned int num_tx_queues; /* 120 4 */ > unsigned int num_lag_ids; /* 124 4 */ > /* --- cacheline 2 boundary (128 bytes) --- */ > unsigned int max_num_bridges; /* 128 4 */ > unsigned int num_ports; /* 132 4 */ > > /* size: 136, cachelines: 3, members: 27 */ > /* sum members: 128, holes: 1, sum holes: 4 */ > /* sum bitfield members: 9 bits, bit holes: 1, sum bit holes: 23 bits */ > /* paddings: 1, sum paddings: 4 */ > /* last cacheline: 8 bytes */ > }; > > Signed-off-by: Vladimir Oltean <vladimir.oltean@nxp.com> Reviewed-by: Florian Fainelli <f.fainelli@gmail.com>
diff --git a/include/net/dsa.h b/include/net/dsa.h index a8a586039033..fef9d8bb5190 100644 --- a/include/net/dsa.h +++ b/include/net/dsa.h @@ -435,7 +435,7 @@ struct dsa_switch { */ unsigned int max_num_bridges; - size_t num_ports; + unsigned int num_ports; }; static inline struct dsa_port *dsa_to_port(struct dsa_switch *ds, int p) diff --git a/net/dsa/dsa2.c b/net/dsa/dsa2.c index c1da813786a4..3d21521453fe 100644 --- a/net/dsa/dsa2.c +++ b/net/dsa/dsa2.c @@ -1475,7 +1475,7 @@ static int dsa_switch_parse_ports_of(struct dsa_switch *ds, } if (reg >= ds->num_ports) { - dev_err(ds->dev, "port %pOF index %u exceeds num_ports (%zu)\n", + dev_err(ds->dev, "port %pOF index %u exceeds num_ports (%u)\n", port, reg, ds->num_ports); of_node_put(port); err = -EINVAL;
Currently, num_ports is declared as size_t, which is defined as __kernel_ulong_t, therefore it occupies 8 bytes of memory. Even switches with port numbers in the range of tens are exotic, so there is no need for this amount of storage. Additionally, because the max_num_bridges member right above it is also 4 bytes, it means the compiler needs to add padding between the last 2 fields. By reducing the size, we don't need that padding and can reduce the struct size. Before: pahole -C dsa_switch net/dsa/slave.o struct dsa_switch { struct device * dev; /* 0 8 */ struct dsa_switch_tree * dst; /* 8 8 */ unsigned int index; /* 16 4 */ u32 setup:1; /* 20: 0 4 */ u32 vlan_filtering_is_global:1; /* 20: 1 4 */ u32 needs_standalone_vlan_filtering:1; /* 20: 2 4 */ u32 configure_vlan_while_not_filtering:1; /* 20: 3 4 */ u32 untag_bridge_pvid:1; /* 20: 4 4 */ u32 assisted_learning_on_cpu_port:1; /* 20: 5 4 */ u32 vlan_filtering:1; /* 20: 6 4 */ u32 pcs_poll:1; /* 20: 7 4 */ u32 mtu_enforcement_ingress:1; /* 20: 8 4 */ /* XXX 23 bits hole, try to pack */ struct notifier_block nb; /* 24 24 */ /* XXX last struct has 4 bytes of padding */ void * priv; /* 48 8 */ void * tagger_data; /* 56 8 */ /* --- cacheline 1 boundary (64 bytes) --- */ struct dsa_chip_data * cd; /* 64 8 */ const struct dsa_switch_ops * ops; /* 72 8 */ u32 phys_mii_mask; /* 80 4 */ /* XXX 4 bytes hole, try to pack */ struct mii_bus * slave_mii_bus; /* 88 8 */ unsigned int ageing_time_min; /* 96 4 */ unsigned int ageing_time_max; /* 100 4 */ struct dsa_8021q_context * tag_8021q_ctx; /* 104 8 */ struct devlink * devlink; /* 112 8 */ unsigned int num_tx_queues; /* 120 4 */ unsigned int num_lag_ids; /* 124 4 */ /* --- cacheline 2 boundary (128 bytes) --- */ unsigned int max_num_bridges; /* 128 4 */ /* XXX 4 bytes hole, try to pack */ size_t num_ports; /* 136 8 */ /* size: 144, cachelines: 3, members: 27 */ /* sum members: 132, holes: 2, sum holes: 8 */ /* sum bitfield members: 9 bits, bit holes: 1, sum bit holes: 23 bits */ /* paddings: 1, sum paddings: 4 */ /* last cacheline: 16 bytes */ }; After: pahole -C dsa_switch net/dsa/slave.o struct dsa_switch { struct device * dev; /* 0 8 */ struct dsa_switch_tree * dst; /* 8 8 */ unsigned int index; /* 16 4 */ u32 setup:1; /* 20: 0 4 */ u32 vlan_filtering_is_global:1; /* 20: 1 4 */ u32 needs_standalone_vlan_filtering:1; /* 20: 2 4 */ u32 configure_vlan_while_not_filtering:1; /* 20: 3 4 */ u32 untag_bridge_pvid:1; /* 20: 4 4 */ u32 assisted_learning_on_cpu_port:1; /* 20: 5 4 */ u32 vlan_filtering:1; /* 20: 6 4 */ u32 pcs_poll:1; /* 20: 7 4 */ u32 mtu_enforcement_ingress:1; /* 20: 8 4 */ /* XXX 23 bits hole, try to pack */ struct notifier_block nb; /* 24 24 */ /* XXX last struct has 4 bytes of padding */ void * priv; /* 48 8 */ void * tagger_data; /* 56 8 */ /* --- cacheline 1 boundary (64 bytes) --- */ struct dsa_chip_data * cd; /* 64 8 */ const struct dsa_switch_ops * ops; /* 72 8 */ u32 phys_mii_mask; /* 80 4 */ /* XXX 4 bytes hole, try to pack */ struct mii_bus * slave_mii_bus; /* 88 8 */ unsigned int ageing_time_min; /* 96 4 */ unsigned int ageing_time_max; /* 100 4 */ struct dsa_8021q_context * tag_8021q_ctx; /* 104 8 */ struct devlink * devlink; /* 112 8 */ unsigned int num_tx_queues; /* 120 4 */ unsigned int num_lag_ids; /* 124 4 */ /* --- cacheline 2 boundary (128 bytes) --- */ unsigned int max_num_bridges; /* 128 4 */ unsigned int num_ports; /* 132 4 */ /* size: 136, cachelines: 3, members: 27 */ /* sum members: 128, holes: 1, sum holes: 4 */ /* sum bitfield members: 9 bits, bit holes: 1, sum bit holes: 23 bits */ /* paddings: 1, sum paddings: 4 */ /* last cacheline: 8 bytes */ }; Signed-off-by: Vladimir Oltean <vladimir.oltean@nxp.com> --- include/net/dsa.h | 2 +- net/dsa/dsa2.c | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-)