Skip to content

Commit 1f32085

Browse files
committed
mctpd: Update interface vtables when we change to BusOwner role
Currently, setting an interface's Role property only sets the link->role. However, we also want to expose the BusOwner1 interface when changing from Unknown to BusOwner, so register the bus_link_owner_vtable on the interface object when this happens. dbus does not like the vtables changing during a call, so we defer this to the main loop context. Fixes: #130 Signed-off-by: Jeremy Kerr <jk@codeconstruct.com.au>
1 parent 07c7a5d commit 1f32085

2 files changed

Lines changed: 35 additions & 0 deletions

File tree

CHANGELOG.md

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,11 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/).
66

77
## [Unreleased]
88

9+
### Fixes
10+
11+
1. mctpd's interface objects now expose the BusOwner1 interface when set
12+
as a BusOwner via the Role property
13+
914
## [2.5] - 2026-02-17
1015

1116
### Added

src/mctpd.c

Lines changed: 30 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -144,6 +144,7 @@ struct link {
144144
char *path;
145145
sd_bus_slot *slot_iface;
146146
sd_bus_slot *slot_busowner;
147+
sd_event_source *role_defer;
147148

148149
struct ctx *ctx;
149150
};
@@ -4023,6 +4024,27 @@ static int bus_link_get_prop(sd_bus *bus, const char *path,
40234024
return rc;
40244025
}
40254026

4027+
/* deferred handler for link changes, which may alter vtable state */
4028+
static int link_set_role(sd_event_source *ev, void *userdata)
4029+
{
4030+
struct link *link = userdata;
4031+
int rc;
4032+
4033+
sd_event_source_unref(link->role_defer);
4034+
link->role_defer = NULL;
4035+
4036+
if (link->role != ENDPOINT_ROLE_BUS_OWNER)
4037+
return 0;
4038+
4039+
rc = sd_bus_add_object_vtable(link->ctx->bus, &link->slot_busowner,
4040+
link->path, CC_MCTP_DBUS_IFACE_BUSOWNER,
4041+
bus_link_owner_vtable, link);
4042+
if (rc)
4043+
warnx("adding link owner vtable failed: %d", rc);
4044+
4045+
return 0;
4046+
}
4047+
40264048
static int bus_link_set_prop(sd_bus *bus, const char *path,
40274049
const char *interface, const char *property,
40284050
sd_bus_message *value, void *userdata,
@@ -4063,8 +4085,15 @@ static int bus_link_set_prop(sd_bus *bus, const char *path,
40634085
rc = -EINVAL;
40644086
goto out;
40654087
}
4088+
4089+
printf("Role for %s set to %s, via dbus\n", link->path, role.conf_val);
40664090
link->role = role.role;
40674091

4092+
/* We need to defer the link role change, as we cannot update the vtables
4093+
* during the call.
4094+
*/
4095+
sd_event_add_defer(ctx->event, &link->role_defer, link_set_role, link);
4096+
40684097
out:
40694098
set_berr(ctx, rc, berr);
40704099
return rc;
@@ -4494,6 +4523,7 @@ static int prune_old_nets(struct ctx *ctx)
44944523

44954524
static void free_link(struct link *link)
44964525
{
4526+
sd_event_source_disable_unref(link->role_defer);
44974527
sd_bus_slot_unref(link->slot_iface);
44984528
sd_bus_slot_unref(link->slot_busowner);
44994529
free(link->path);

0 commit comments

Comments
 (0)