summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorMatthias Beyer <matthias.beyer@ifm.com>2022-08-18 14:14:19 +0200
committerMatthias Beyer <matthias.beyer@ifm.com>2022-08-30 13:54:48 +0200
commit1ce887b567fd56a65deed1ab09c1dd927f3087bf (patch)
tree10051f888d5d11101f54685c4ae10542dc4520b7
parentff6e4924f4de83eeb3b99c5321c8038b9c0a51be (diff)
-rw-r--r--Cargo.lock1
-rw-r--r--plugins/plugin_lua/Cargo.toml1
-rw-r--r--plugins/plugin_lua/src/builder.rs18
-rw-r--r--plugins/plugin_lua/src/config.rs6
-rw-r--r--plugins/plugin_lua/src/error.rs5
-rw-r--r--plugins/plugin_lua/src/plugin.rs30
6 files changed, 53 insertions, 8 deletions
diff --git a/Cargo.lock b/Cargo.lock
index 07e6bd28..fe9e92be 100644
--- a/Cargo.lock
+++ b/Cargo.lock
@@ -2518,6 +2518,7 @@ dependencies = [
"tedge_api",
"tedge_lib",
"thiserror",
+ "tokio",
"toml",
"tracing",
]
diff --git a/plugins/plugin_lua/Cargo.toml b/plugins/plugin_lua/Cargo.toml
index 71f5899e..92c6bbda 100644
--- a/plugins/plugin_lua/Cargo.toml
+++ b/plugins/plugin_lua/Cargo.toml
@@ -14,6 +14,7 @@ serde_with = "1"
thiserror = "1"
toml = "0.5"
tracing = "0.1"
+tokio = { version = "1", features = ["sync"] }
tedge_api = { path = "../../crates/core/tedge_api" }
tedge_lib = { path = "../../crates/core/tedge_lib" }
diff --git a/plugins/plugin_lua/src/builder.rs b/plugins/plugin_lua/src/builder.rs
index 86f160dd..3e7f8d87 100644
--- a/plugins/plugin_lua/src/builder.rs
+++ b/plugins/plugin_lua/src/builder.rs
@@ -37,10 +37,18 @@ impl<PD: PluginDirectory> PluginBuilder<PD> for LuaPluginBuilder {
) -> Result<(), tedge_api::error::PluginError> {
config
.clone()
- .try_into()
- .map(|_: Config| ())
+ .try_into::<Config>()
.map_err(crate::error::Error::ConfigParseFailed)
- .map_err(PluginError::from)
+ .and_then(|config| {
+ if !config.script.exists() {
+ Err(crate::error::Error::ScriptDoesNotExist(
+ config.script.clone(),
+ ))
+ } else {
+ Ok(())
+ }
+ })
+ .map_err(tedge_api::error::PluginError::from)
}
async fn instantiate(
@@ -49,11 +57,11 @@ impl<PD: PluginDirectory> PluginBuilder<PD> for LuaPluginBuilder {
_cancellation_token: CancellationToken,
_plugin_dir: &PD,
) -> Result<BuiltPlugin, PluginError> {
- let _config = config
+ let config = config
.try_into::<Config>()
.map_err(crate::error::Error::ConfigParseFailed)
.map_err(PluginError::from)?;
- Ok(LuaPlugin::new().finish())
+ Ok(LuaPlugin::new(&config).finish())
}
}
diff --git a/plugins/plugin_lua/src/config.rs b/plugins/plugin_lua/src/config.rs
index 46eac953..eb197bd9 100644
--- a/plugins/plugin_lua/src/config.rs
+++ b/plugins/plugin_lua/src/config.rs
@@ -4,4 +4,10 @@ use std::path::PathBuf;
pub struct Config {
/// The path to the script to execute
pub(crate) script: PathBuf,
+
+ /// How much memory the lua virtual machine can allocate
+ ///
+ /// If not specified, no memory limit is set, which means that the lua process can OOM the
+ /// system.
+ pub(crate) memory_limit: Option<tedge_lib::config::ByteSize>,
}
diff --git a/plugins/plugin_lua/src/error.rs b/plugins/plugin_lua/src/error.rs
index 0c04533b..e7d3f801 100644
--- a/plugins/plugin_lua/src/error.rs
+++ b/plugins/plugin_lua/src/error.rs
@@ -1,6 +1,11 @@
+use std::path::PathBuf;
+
#[derive(Debug, miette::Diagnostic, thiserror::Error)]
#[allow(clippy::enum_variant_names)]
pub(crate) enum Error {
#[error("Failed to parse configuration")]
ConfigParseFailed(toml::de::Error),
+
+ #[error("Script does not exist: {0}")]
+ ScriptDoesNotExist(PathBuf),
}
diff --git a/plugins/plugin_lua/src/plugin.rs b/plugins/plugin_lua/src/plugin.rs
index 7f8e01c4..188b1412 100644
--- a/plugins/plugin_lua/src/plugin.rs
+++ b/plugins/plugin_lua/src/plugin.rs
@@ -1,13 +1,37 @@
+use std::sync::Arc;
+
use async_trait::async_trait;
+use rlua::Lua;
use tedge_api::Plugin;
use tedge_api::PluginError;
+use tokio::sync::RwLock;
+
+use crate::config::Config;
#[derive(Debug)]
-pub struct LuaPlugin;
+pub struct LuaPlugin {
+ lua: RwLock<Lua>,
+}
impl LuaPlugin {
- pub(crate) fn new() -> Self {
- LuaPlugin
+ pub(crate) fn new(config: &Config) -> Self {
+ LuaPlugin {
+ lua: {
+ let lua = rlua::Lua::new();
+ let memory_limit = config.memory_limit.map(|bs| {
+ let bs = bs.into_bytesize().as_u64();
+ if (usize::MAX as u64) < bs {
+ usize::MAX
+ } else {
+ bs as usize
+ }
+ });
+
+ lua.set_memory_limit(memory_limit);
+
+ RwLock::new(lua)
+ },
+ }
}
}