Mutability conflicts between various skeleton-based accessors
The skeleton-based accessors (bss, rodata, ...) tend to conflict with other reasonable-to-call methods, such as maps().
For example, from capable:
impl OpenCapableSkel<'_> {
pub fn progs(&self) -> OpenCapableProgs<'_> {
OpenCapableProgs { inner: &self.obj }
}
pub fn progs_mut(&mut self) -> OpenCapableProgsMut<'_> {
OpenCapableProgsMut {
inner: &mut self.obj,
}
}
pub fn maps(&self) -> OpenCapableMaps<'_> {
OpenCapableMaps { inner: &self.obj }
}
pub fn maps_mut(&mut self) -> OpenCapableMapsMut<'_> {
OpenCapableMapsMut {
inner: &mut self.obj,
}
}
pub fn rodata(&mut self) -> &'_ mut capable_rodata_types::rodata {
unsafe {
std::mem::transmute::<*mut std::ffi::c_void, &'_ mut capable_rodata_types::rodata>(
self.skel_config.map_mmap_ptr(2).unwrap(),
)
}
}
pub fn bss(&mut self) -> &'_ mut capable_bss_types::bss {
unsafe {
std::mem::transmute::<*mut std::ffi::c_void, &'_ mut capable_bss_types::bss>(
self.skel_config.map_mmap_ptr(3).unwrap(),
)
}
}
pub fn kconfig(&mut self) -> &'_ mut capable_kconfig_types::kconfig {
unsafe {
std::mem::transmute::<*mut std::ffi::c_void, &'_ mut capable_kconfig_types::kconfig>(
self.skel_config.map_mmap_ptr(4).unwrap(),
)
}
}
}
If you have a bss reference you can't have rodata as well. As a first step, we may want to add *_mut variants, similar to what we do for maps. But really this is all rather...painful to use by clients. We should see if we can improve usability in general. Conceptually there is no connection between those calls, and yet they can conflict.
To give an update: This issue has been mitigated in some part by https://github.com/libbpf/libbpf-rs/commit/a00ee2d5e0834c7f8764006689321dd4bca8653a and https://github.com/libbpf/libbpf-rs/commit/855eb8422e98e4632d433d5fbf065ab703674fbf. But that does not cover all issues: you can still have conflicts between a shared borrow of, say, bss and an exclusive one of rodata