On 16 Mar 2022, at 19:51, Mike Pattrick wrote:
> Currently we allocate and format a string in dp_netdev_flow_add in case > miniflow_bits needs to be printed by dpctl/dump-flows/get-flow. However, > this adds unneeded calls to realloc in the pmd hot path, while > the resulting string may never be viewed. > > Instead of keeping a pointer to an allocated string, now we just keep > track of the 16 byte flow map. Harry can you take a look at this, as this was added as part of MFEX. At a first glance, the only thing I see is that “dp-extra-info” is/was a general dp type independent string, and now it has become something for a specific dp and use case. //Eelco > Signed-off-by: Mike Pattrick <m...@redhat.com> > --- > lib/dpctl.c | 13 +++++++++++-- > lib/dpif-netdev-private-flow.h | 2 +- > lib/dpif-netdev.c | 15 +-------------- > lib/dpif-netlink.c | 2 +- > lib/dpif.h | 6 +++--- > lib/flow.h | 1 + > lib/netdev-offload-dpdk.c | 2 +- > lib/netdev-offload-tc.c | 2 +- > 8 files changed, 20 insertions(+), 23 deletions(-) > > diff --git a/lib/dpctl.c b/lib/dpctl.c > index 29041fa3e..6ff26fb1b 100644 > --- a/lib/dpctl.c > +++ b/lib/dpctl.c > @@ -876,8 +876,17 @@ format_dpif_flow(struct ds *ds, const struct dpif_flow > *f, struct hmap *ports, > } > ds_put_cstr(ds, ", actions:"); > format_odp_actions(ds, f->actions, f->actions_len, ports); > - if (dpctl_p->verbosity && f->attrs.dp_extra_info) { > - ds_put_format(ds, ", dp-extra-info:%s", f->attrs.dp_extra_info); > + if (dpctl_p->verbosity && !flowmap_is_empty(f->attrs.dp_extra_info)) { > + size_t unit; > + ds_put_cstr(ds, ", dp-extra-info:miniflow_bits("); > + FLOWMAP_FOR_EACH_UNIT (unit) { > + if (unit) { > + ds_put_char(ds, ','); > + } > + ds_put_format(ds, "%d", > + count_1bits(f->attrs.dp_extra_info.bits[unit])); > + } > + ds_put_char(ds, ')'); > } > } > > diff --git a/lib/dpif-netdev-private-flow.h b/lib/dpif-netdev-private-flow.h > index 66016eb09..a99257251 100644 > --- a/lib/dpif-netdev-private-flow.h > +++ b/lib/dpif-netdev-private-flow.h > @@ -123,7 +123,7 @@ struct dp_netdev_flow { > struct packet_batch_per_flow *batch; > > /* Packet classification. */ > - char *dp_extra_info; /* String to return in a flow dump/get. */ > + struct flowmap dp_extra_info; > struct dpcls_rule cr; /* In owning dp_netdev's 'cls'. */ > /* 'cr' must be the last member. */ > }; > diff --git a/lib/dpif-netdev.c b/lib/dpif-netdev.c > index 720818e30..380274a3a 100644 > --- a/lib/dpif-netdev.c > +++ b/lib/dpif-netdev.c > @@ -2380,7 +2380,6 @@ static void > dp_netdev_flow_free(struct dp_netdev_flow *flow) > { > dp_netdev_actions_free(dp_netdev_flow_get_actions(flow)); > - free(flow->dp_extra_info); > free(flow); > } > > @@ -4058,11 +4057,9 @@ dp_netdev_flow_add(struct dp_netdev_pmd_thread *pmd, > odp_port_t orig_in_port) > OVS_REQUIRES(pmd->flow_mutex) > { > - struct ds extra_info = DS_EMPTY_INITIALIZER; > struct dp_netdev_flow *flow; > struct netdev_flow_key mask; > struct dpcls *cls; > - size_t unit; > > /* Make sure in_port is exact matched before we read it. */ > ovs_assert(match->wc.masks.in_port.odp_port == ODPP_NONE); > @@ -4106,17 +4103,7 @@ dp_netdev_flow_add(struct dp_netdev_pmd_thread *pmd, > cls = dp_netdev_pmd_find_dpcls(pmd, in_port); > dpcls_insert(cls, &flow->cr, &mask); > > - ds_put_cstr(&extra_info, "miniflow_bits("); > - FLOWMAP_FOR_EACH_UNIT (unit) { > - if (unit) { > - ds_put_char(&extra_info, ','); > - } > - ds_put_format(&extra_info, "%d", > - count_1bits(flow->cr.mask->mf.map.bits[unit])); > - } > - ds_put_char(&extra_info, ')'); > - flow->dp_extra_info = ds_steal_cstr(&extra_info); > - ds_destroy(&extra_info); > + flow->dp_extra_info = flow->cr.mask->mf.map; > > cmap_insert(&pmd->flow_table, CONST_CAST(struct cmap_node *, > &flow->node), > dp_netdev_flow_hash(&flow->ufid)); > diff --git a/lib/dpif-netlink.c b/lib/dpif-netlink.c > index 71e35ccdd..a63c6ac8f 100644 > --- a/lib/dpif-netlink.c > +++ b/lib/dpif-netlink.c > @@ -1768,7 +1768,7 @@ dpif_netlink_flow_to_dpif_flow(struct dpif_flow > *dpif_flow, > dpif_netlink_flow_get_stats(datapath_flow, &dpif_flow->stats); > dpif_flow->attrs.offloaded = false; > dpif_flow->attrs.dp_layer = "ovs"; > - dpif_flow->attrs.dp_extra_info = NULL; > + dpif_flow->attrs.dp_extra_info = FLOWMAP_EMPTY_MAP; > } > > /* The design is such that all threads are working together on the first dump > diff --git a/lib/dpif.h b/lib/dpif.h > index 6cb4dae6d..6fd46ef94 100644 > --- a/lib/dpif.h > +++ b/lib/dpif.h > @@ -515,9 +515,9 @@ struct dpif_flow_detailed_stats { > }; > > struct dpif_flow_attrs { > - bool offloaded; /* True if flow is offloaded to HW. */ > - const char *dp_layer; /* DP layer the flow is handled in. */ > - const char *dp_extra_info; /* Extra information provided by DP. */ > + bool offloaded; /* True if flow is offloaded to HW. */ > + const char *dp_layer; /* DP layer the flow is handled in. */ > + struct flowmap dp_extra_info; /* Extra information provided by DP. */ > }; > > struct dpif_flow_dump_types { > diff --git a/lib/flow.h b/lib/flow.h > index c647ad83c..5d8481add 100644 > --- a/lib/flow.h > +++ b/lib/flow.h > @@ -283,6 +283,7 @@ struct flowmap { > }; > > #define FLOWMAP_EMPTY_INITIALIZER { { 0 } } > +static const struct flowmap FLOWMAP_EMPTY_MAP = FLOWMAP_EMPTY_INITIALIZER; > > static inline void flowmap_init(struct flowmap *); > static inline bool flowmap_equal(struct flowmap, struct flowmap); > diff --git a/lib/netdev-offload-dpdk.c b/lib/netdev-offload-dpdk.c > index 94dc6a9b7..d18cbaa5c 100644 > --- a/lib/netdev-offload-dpdk.c > +++ b/lib/netdev-offload-dpdk.c > @@ -2458,7 +2458,7 @@ netdev_offload_dpdk_flow_get(struct netdev *netdev, > struct rte_flow_error error; > int ret = 0; > > - attrs->dp_extra_info = NULL; > + attrs->dp_extra_info = FLOWMAP_EMPTY_MAP; > > rte_flow_data = ufid_to_rte_flow_data_find(netdev, ufid, false); > if (!rte_flow_data || !rte_flow_data->rte_flow || > diff --git a/lib/netdev-offload-tc.c b/lib/netdev-offload-tc.c > index 3f7068c8e..1d47eb624 100644 > --- a/lib/netdev-offload-tc.c > +++ b/lib/netdev-offload-tc.c > @@ -600,7 +600,7 @@ parse_tc_flower_to_attrs(struct tc_flower *flower, > flower->offloaded_state == > TC_OFFLOADED_STATE_UNDEFINED); > attrs->dp_layer = "tc"; > - attrs->dp_extra_info = NULL; > + attrs->dp_extra_info = FLOWMAP_EMPTY_MAP; > } > > static int > -- > 2.27.0 > > _______________________________________________ > dev mailing list > d...@openvswitch.org > https://mail.openvswitch.org/mailman/listinfo/ovs-dev _______________________________________________ dev mailing list d...@openvswitch.org https://mail.openvswitch.org/mailman/listinfo/ovs-dev