@@ -276,6 +276,7 @@ static int add_peer_from_addr(struct ctx *ctx,
276276 const struct sockaddr_mctp_ext * addr ,
277277 struct peer * * ret_peer );
278278static int remove_peer (struct peer * peer );
279+ static int remove_bridged_peers (struct peer * bridge );
279280static int query_peer_properties (struct peer * peer );
280281static int setup_added_peer (struct peer * peer );
281282static void add_peer_route (struct peer * peer );
@@ -1882,6 +1883,54 @@ static int check_peer_struct(const struct peer *peer, const struct net *n)
18821883 return 0 ;
18831884}
18841885
1886+ /* Stops downstream endpoint polling and removes
1887+ * peer structure when bridge endpoint is being removed.
1888+ */
1889+ static int remove_bridged_peers (struct peer * bridge )
1890+ {
1891+ mctp_eid_t ep , pool_start , pool_end ;
1892+ struct poll_ctx * pctx = NULL ;
1893+ struct peer * peer = NULL ;
1894+ struct net * n = NULL ;
1895+ int rc = 0 ;
1896+
1897+ pool_end = bridge -> pool_start + bridge -> pool_size - 1 ;
1898+ n = lookup_net (bridge -> ctx , bridge -> net );
1899+ pool_start = bridge -> pool_start ;
1900+ for (ep = pool_start ; ep <= pool_end ; ep ++ ) {
1901+ // stop endpoint polling before removing peer
1902+ // else next trigger will create peer again.
1903+ int idx = ep - pool_start ;
1904+
1905+ if (bridge -> poll .sources && bridge -> poll .sources [idx ]) {
1906+ pctx = sd_event_source_get_userdata (
1907+ bridge -> poll .sources [idx ]);
1908+ rc = sd_event_source_set_enabled (
1909+ bridge -> poll .sources [idx ], SD_EVENT_OFF );
1910+ if (rc < 0 ) {
1911+ warnx ("Failed to stop polling timer while removing peer %d: %s" ,
1912+ ep , strerror (- rc ));
1913+ }
1914+
1915+ sd_event_source_unref (bridge -> poll .sources [idx ]);
1916+ bridge -> poll .sources [idx ] = NULL ;
1917+ free (pctx );
1918+ }
1919+ peer = n -> peers [ep ];
1920+ if (!peer )
1921+ continue ;
1922+
1923+ rc = remove_peer (peer );
1924+ if (rc < 0 ) {
1925+ warnx ("Failed to remove peer %d from bridge eid %d pool [%d - %d]: %s" ,
1926+ ep , bridge -> eid , pool_start , pool_end ,
1927+ strerror (- rc ));
1928+ }
1929+ }
1930+
1931+ return 0 ;
1932+ }
1933+
18851934static int remove_peer (struct peer * peer )
18861935{
18871936 struct ctx * ctx = peer -> ctx ;
@@ -1916,6 +1965,12 @@ static int remove_peer(struct peer *peer)
19161965 sd_event_source_unref (peer -> recovery .source );
19171966 }
19181967
1968+ if (peer -> pool_size ) {
1969+ remove_bridged_peers (peer );
1970+ free (peer -> poll .sources );
1971+ peer -> poll .sources = NULL ;
1972+ }
1973+
19191974 n -> peers [peer -> eid ] = NULL ;
19201975 free (peer -> message_types );
19211976 free (peer -> uuid );
@@ -1962,6 +2017,7 @@ static void free_peers(struct ctx *ctx)
19622017 free (peer -> message_types );
19632018 free (peer -> uuid );
19642019 free (peer -> path );
2020+ free (peer -> poll .sources );
19652021 sd_bus_slot_unref (peer -> slot_obmc_endpoint );
19662022 sd_bus_slot_unref (peer -> slot_cc_endpoint );
19672023 sd_bus_slot_unref (peer -> slot_bridge );
0 commit comments