mirror of
https://github.com/bevyengine/bevy
synced 2024-11-21 20:23:28 +00:00
Remove deprecated bevy_dynamic_plugin
(#14534)
# Objective - Dynamic plugins were deprecated in #13080 due to being unsound. The plan was to deprecate them in 0.14 and remove them in 0.15. ## Solution - Remove all dynamic plugin functionality. - Update documentation to reflect this change. --- ## Migration Guide Dynamic plugins were deprecated in 0.14 for being unsound, and they have now been fully removed. Please consider using the alternatives listed in the `bevy_dynamic_plugin` crate documentation, or worst-case scenario you may copy the code from 0.14.
This commit is contained in:
parent
9575b20d31
commit
d722fef23d
15 changed files with 2 additions and 219 deletions
|
@ -110,9 +110,6 @@ bevy_core_pipeline = [
|
|||
"bevy_render",
|
||||
]
|
||||
|
||||
# Plugin for dynamic loading (using [libloading](https://crates.io/crates/libloading))
|
||||
bevy_dynamic_plugin = ["bevy_internal/bevy_dynamic_plugin"]
|
||||
|
||||
# Adds gamepad support
|
||||
bevy_gilrs = ["bevy_internal/bevy_gilrs"]
|
||||
|
||||
|
|
|
@ -18,7 +18,6 @@ mod sub_app;
|
|||
mod terminal_ctrl_c_handler;
|
||||
|
||||
pub use app::*;
|
||||
pub use bevy_derive::DynamicPlugin;
|
||||
pub use main_schedule::*;
|
||||
pub use panic_handler::*;
|
||||
pub use plugin::*;
|
||||
|
@ -38,6 +37,6 @@ pub mod prelude {
|
|||
PostStartup, PostUpdate, PreStartup, PreUpdate, SpawnScene, Startup, Update,
|
||||
},
|
||||
sub_app::SubApp,
|
||||
DynamicPlugin, Plugin, PluginGroup,
|
||||
Plugin, PluginGroup,
|
||||
};
|
||||
}
|
||||
|
|
|
@ -120,16 +120,6 @@ impl Plugin for PlaceholderPlugin {
|
|||
fn build(&self, _app: &mut App) {}
|
||||
}
|
||||
|
||||
/// A type representing an unsafe function that returns a mutable pointer to a [`Plugin`].
|
||||
/// It is used for dynamically loading plugins.
|
||||
///
|
||||
/// See `bevy_dynamic_plugin/src/loader.rs#dynamically_load_plugin`.
|
||||
#[deprecated(
|
||||
since = "0.14.0",
|
||||
note = "The current dynamic plugin system is unsound and will be removed in 0.15."
|
||||
)]
|
||||
pub type CreatePlugin = unsafe fn() -> *mut dyn Plugin;
|
||||
|
||||
/// Types that represent a set of [`Plugin`]s.
|
||||
///
|
||||
/// This is implemented for all types which implement [`Plugin`],
|
||||
|
|
|
@ -1,22 +0,0 @@
|
|||
use proc_macro::TokenStream;
|
||||
use quote::quote;
|
||||
use syn::{parse_macro_input, DeriveInput};
|
||||
|
||||
#[deprecated(
|
||||
since = "0.14.0",
|
||||
note = "The current dynamic plugin system is unsound and will be removed in 0.15."
|
||||
)]
|
||||
pub fn derive_dynamic_plugin(input: TokenStream) -> TokenStream {
|
||||
let ast = parse_macro_input!(input as DeriveInput);
|
||||
let struct_name = &ast.ident;
|
||||
|
||||
TokenStream::from(quote! {
|
||||
#[no_mangle]
|
||||
pub extern "C" fn _bevy_create_plugin() -> *mut dyn bevy::app::Plugin {
|
||||
// make sure the constructor is the correct type.
|
||||
let object = #struct_name {};
|
||||
let boxed = Box::new(object);
|
||||
Box::into_raw(boxed)
|
||||
}
|
||||
})
|
||||
}
|
|
@ -9,7 +9,6 @@
|
|||
|
||||
extern crate proc_macro;
|
||||
|
||||
mod app_plugin;
|
||||
mod bevy_main;
|
||||
mod derefs;
|
||||
mod enum_variant_meta;
|
||||
|
@ -18,19 +17,6 @@ use bevy_macro_utils::{derive_label, BevyManifest};
|
|||
use proc_macro::TokenStream;
|
||||
use quote::format_ident;
|
||||
|
||||
/// Generates a dynamic plugin entry point function for the given `Plugin` type.
|
||||
///
|
||||
/// This is deprecated since 0.14. The current dynamic plugin system is unsound and will be removed in 0.15.
|
||||
#[proc_macro_derive(DynamicPlugin)]
|
||||
#[deprecated(
|
||||
since = "0.14.0",
|
||||
note = "The current dynamic plugin system is unsound and will be removed in 0.15."
|
||||
)]
|
||||
pub fn derive_dynamic_plugin(input: TokenStream) -> TokenStream {
|
||||
#[allow(deprecated)]
|
||||
app_plugin::derive_dynamic_plugin(input)
|
||||
}
|
||||
|
||||
/// Implements [`Deref`] for structs. This is especially useful when utilizing the [newtype] pattern.
|
||||
///
|
||||
/// For single-field structs, the implementation automatically uses that field.
|
||||
|
|
|
@ -31,7 +31,7 @@ sysinfo = { version = "0.30.0", optional = true, default-features = false, featu
|
|||
"apple-app-store",
|
||||
] }
|
||||
|
||||
# Only include when not bevy_dynamic_plugin and on linux/windows/android
|
||||
# Only include when on linux/windows/android
|
||||
[target.'cfg(any(target_os = "linux", target_os = "windows", target_os = "android"))'.dependencies]
|
||||
sysinfo = { version = "0.30.0", optional = true, default-features = false }
|
||||
|
||||
|
|
|
@ -1,24 +0,0 @@
|
|||
[package]
|
||||
name = "bevy_dynamic_plugin"
|
||||
version = "0.15.0-dev"
|
||||
edition = "2021"
|
||||
description = "Provides dynamic plugin loading capabilities for non-wasm platforms"
|
||||
homepage = "https://bevyengine.org"
|
||||
repository = "https://github.com/bevyengine/bevy"
|
||||
license = "MIT OR Apache-2.0"
|
||||
keywords = ["bevy"]
|
||||
|
||||
[dependencies]
|
||||
# bevy
|
||||
bevy_app = { path = "../bevy_app", version = "0.15.0-dev" }
|
||||
|
||||
# other
|
||||
libloading = { version = "0.8" }
|
||||
thiserror = "1.0"
|
||||
|
||||
[lints]
|
||||
workspace = true
|
||||
|
||||
[package.metadata.docs.rs]
|
||||
rustdoc-args = ["-Zunstable-options", "--generate-link-to-definition"]
|
||||
all-features = true
|
|
@ -1,7 +0,0 @@
|
|||
# Bevy Dynamic Plugin
|
||||
|
||||
[![License](https://img.shields.io/badge/license-MIT%2FApache-blue.svg)](https://github.com/bevyengine/bevy#license)
|
||||
[![Crates.io](https://img.shields.io/crates/v/bevy_dynamic_plugin.svg)](https://crates.io/crates/bevy_dynamic_plugin)
|
||||
[![Downloads](https://img.shields.io/crates/d/bevy_dynamic_plugin.svg)](https://crates.io/crates/bevy_dynamic_plugin)
|
||||
[![Docs](https://docs.rs/bevy_dynamic_plugin/badge.svg)](https://docs.rs/bevy_dynamic_plugin/latest/bevy_dynamic_plugin/)
|
||||
[![Discord](https://img.shields.io/discord/691052431525675048.svg?label=&logo=discord&logoColor=ffffff&color=7389D8&labelColor=6A7EC2)](https://discord.gg/bevy)
|
|
@ -1,41 +0,0 @@
|
|||
#![cfg_attr(docsrs, feature(doc_auto_cfg))]
|
||||
#![doc(
|
||||
html_logo_url = "https://bevyengine.org/assets/icon.png",
|
||||
html_favicon_url = "https://bevyengine.org/assets/icon.png"
|
||||
)]
|
||||
|
||||
//! Bevy's dynamic plugin loading functionality.
|
||||
//!
|
||||
//! This crate allows loading dynamic libraries (`.dylib`, `.so`) that export a single
|
||||
//! [`Plugin`](bevy_app::Plugin). For usage, see [`dynamically_load_plugin`].
|
||||
//!
|
||||
//! # Deprecation
|
||||
//!
|
||||
//! The current dynamic plugin system is unsound and will be removed in 0.15. You may be interested
|
||||
//! in the [Alternatives](#alternatives) listed below. If your use-case is not supported, please
|
||||
//! consider commenting on [#13080](https://github.com/bevyengine/bevy/pull/13080) describing how
|
||||
//! you use dynamic plugins in your project.
|
||||
//!
|
||||
//! # Warning
|
||||
//!
|
||||
//! Note that dynamic linking and loading is inherently unsafe because it allows executing foreign
|
||||
//! code. Additionally, Rust does not have a stable ABI and may produce
|
||||
//! incompatible libraries across Rust versions, or even subsequent compilations. This will not work
|
||||
//! well in scenarios such as modding, but can work if the dynamic plugins and the main app are
|
||||
//! built at the same time, such as with Downloadable Content (DLC) packs.
|
||||
//!
|
||||
//! # Alternatives
|
||||
//!
|
||||
//! You may be interested in these safer alternatives:
|
||||
//!
|
||||
//! - [Bevy Assets - Scripting]: Scripting and modding libraries for Bevy
|
||||
//! - [Bevy Assets - Development tools]: Hot reloading and other development functionality
|
||||
//! - [`stabby`]: Stable Rust ABI
|
||||
//!
|
||||
//! [Bevy Assets - Scripting]: https://bevyengine.org/assets/#scripting
|
||||
//! [Bevy Assets - Development tools]: https://bevyengine.org/assets/#development-tools
|
||||
//! [`stabby`]: https://github.com/ZettaScaleLabs/stabby
|
||||
|
||||
mod loader;
|
||||
|
||||
pub use loader::*;
|
|
@ -1,86 +0,0 @@
|
|||
#![allow(unsafe_code)]
|
||||
#![allow(deprecated)]
|
||||
|
||||
use libloading::{Library, Symbol};
|
||||
use std::ffi::OsStr;
|
||||
use thiserror::Error;
|
||||
|
||||
use bevy_app::{App, CreatePlugin, Plugin};
|
||||
|
||||
/// Errors that can occur when loading a dynamic plugin
|
||||
#[derive(Debug, Error)]
|
||||
#[deprecated(
|
||||
since = "0.14.0",
|
||||
note = "The current dynamic plugin system is unsound and will be removed in 0.15."
|
||||
)]
|
||||
pub enum DynamicPluginLoadError {
|
||||
/// An error occurred when loading a dynamic library.
|
||||
#[error("cannot load library for dynamic plugin: {0}")]
|
||||
Library(#[source] libloading::Error),
|
||||
/// An error occurred when loading a library without a valid Bevy plugin.
|
||||
#[error("dynamic library does not contain a valid Bevy dynamic plugin")]
|
||||
Plugin(#[source] libloading::Error),
|
||||
}
|
||||
|
||||
/// Dynamically links a plugin at the given path. The plugin must export a function with the
|
||||
/// [`CreatePlugin`] signature named `_bevy_create_plugin`.
|
||||
///
|
||||
/// # Safety
|
||||
///
|
||||
/// The specified plugin must be linked against the exact same `libbevy.so` as this program.
|
||||
/// In addition the `_bevy_create_plugin` symbol must not be manually created, but instead created
|
||||
/// by deriving `DynamicPlugin` on a unit struct implementing [`Plugin`].
|
||||
///
|
||||
/// Dynamically loading plugins is orchestrated through dynamic linking. When linking against
|
||||
/// foreign code, initialization routines may be run (as well as termination routines when the
|
||||
/// program exits). The caller of this function is responsible for ensuring these routines are
|
||||
/// sound. For more information, please see the safety section of [`libloading::Library::new`].
|
||||
#[deprecated(
|
||||
since = "0.14.0",
|
||||
note = "The current dynamic plugin system is unsound and will be removed in 0.15."
|
||||
)]
|
||||
pub unsafe fn dynamically_load_plugin<P: AsRef<OsStr>>(
|
||||
path: P,
|
||||
) -> Result<(Library, Box<dyn Plugin>), DynamicPluginLoadError> {
|
||||
// SAFETY: Caller must follow the safety requirements of Library::new.
|
||||
let lib = unsafe { Library::new(path).map_err(DynamicPluginLoadError::Library)? };
|
||||
|
||||
// SAFETY: Loaded plugins are not allowed to specify `_bevy_create_plugin` symbol manually, but
|
||||
// must instead automatically generate it through `DynamicPlugin`.
|
||||
let func: Symbol<CreatePlugin> = unsafe {
|
||||
lib.get(b"_bevy_create_plugin")
|
||||
.map_err(DynamicPluginLoadError::Plugin)?
|
||||
};
|
||||
|
||||
// SAFETY: `func` is automatically generated and is guaranteed to return a pointer created using
|
||||
// `Box::into_raw`.
|
||||
let plugin = unsafe { Box::from_raw(func()) };
|
||||
|
||||
Ok((lib, plugin))
|
||||
}
|
||||
|
||||
/// An extension trait for [`App`] that allows loading dynamic plugins.
|
||||
#[deprecated(
|
||||
since = "0.14.0",
|
||||
note = "The current dynamic plugin system is unsound and will be removed in 0.15."
|
||||
)]
|
||||
pub trait DynamicPluginExt {
|
||||
/// Dynamically links a plugin at the given path, registering the plugin.
|
||||
///
|
||||
/// For more details, see [`dynamically_load_plugin`].
|
||||
///
|
||||
/// # Safety
|
||||
///
|
||||
/// See [`dynamically_load_plugin`]'s safety section.
|
||||
unsafe fn load_plugin<P: AsRef<OsStr>>(&mut self, path: P) -> &mut Self;
|
||||
}
|
||||
|
||||
impl DynamicPluginExt for App {
|
||||
unsafe fn load_plugin<P: AsRef<OsStr>>(&mut self, path: P) -> &mut Self {
|
||||
// SAFETY: Follows the same safety requirements as `dynamically_load_plugin`.
|
||||
let (lib, plugin) = unsafe { dynamically_load_plugin(path).unwrap() };
|
||||
std::mem::forget(lib); // Ensure that the library is not automatically unloaded
|
||||
plugin.build(self);
|
||||
self
|
||||
}
|
||||
}
|
|
@ -230,7 +230,6 @@ bevy_audio = { path = "../bevy_audio", optional = true, version = "0.15.0-dev" }
|
|||
bevy_color = { path = "../bevy_color", optional = true, version = "0.15.0-dev" }
|
||||
bevy_core_pipeline = { path = "../bevy_core_pipeline", optional = true, version = "0.15.0-dev" }
|
||||
bevy_dev_tools = { path = "../bevy_dev_tools", optional = true, version = "0.15.0-dev" }
|
||||
bevy_dynamic_plugin = { path = "../bevy_dynamic_plugin", optional = true, version = "0.15.0-dev" }
|
||||
bevy_gilrs = { path = "../bevy_gilrs", optional = true, version = "0.15.0-dev" }
|
||||
bevy_gizmos = { path = "../bevy_gizmos", optional = true, version = "0.15.0-dev", default-features = false }
|
||||
bevy_gltf = { path = "../bevy_gltf", optional = true, version = "0.15.0-dev" }
|
||||
|
|
|
@ -29,8 +29,6 @@ pub use bevy_core_pipeline as core_pipeline;
|
|||
#[cfg(feature = "bevy_dev_tools")]
|
||||
pub use bevy_dev_tools as dev_tools;
|
||||
pub use bevy_diagnostic as diagnostic;
|
||||
#[cfg(feature = "bevy_dynamic_plugin")]
|
||||
pub use bevy_dynamic_plugin as dynamic_plugin;
|
||||
pub use bevy_ecs as ecs;
|
||||
#[cfg(feature = "bevy_gilrs")]
|
||||
pub use bevy_gilrs as gilrs;
|
||||
|
|
|
@ -51,10 +51,6 @@ pub use crate::text::prelude::*;
|
|||
#[cfg(feature = "bevy_ui")]
|
||||
pub use crate::ui::prelude::*;
|
||||
|
||||
#[doc(hidden)]
|
||||
#[cfg(feature = "bevy_dynamic_plugin")]
|
||||
pub use crate::dynamic_plugin::*;
|
||||
|
||||
#[doc(hidden)]
|
||||
#[cfg(feature = "bevy_gizmos")]
|
||||
pub use crate::gizmos::prelude::*;
|
||||
|
|
|
@ -54,7 +54,6 @@ The default feature set enables most of the expected features of a game engine,
|
|||
|bevy_ci_testing|Enable systems that allow for automated testing on CI|
|
||||
|bevy_debug_stepping|Enable stepping-based debugging of Bevy systems|
|
||||
|bevy_dev_tools|Provides a collection of developer tools|
|
||||
|bevy_dynamic_plugin|Plugin for dynamic loading (using [libloading](https://crates.io/crates/libloading))|
|
||||
|bmp|BMP image format support|
|
||||
|dds|DDS compressed texture support|
|
||||
|debug_glam_assert|Enable assertions in debug builds to check the validity of parameters passed to glam|
|
||||
|
|
|
@ -16,7 +16,6 @@ crates=(
|
|||
bevy_app
|
||||
bevy_time
|
||||
bevy_log
|
||||
bevy_dynamic_plugin
|
||||
bevy_asset/macros
|
||||
bevy_asset
|
||||
bevy_audio
|
||||
|
|
Loading…
Reference in a new issue