Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Adding the basics of a plugin system (WIP) #269

Open
wants to merge 5 commits into
base: master
Choose a base branch
from

Conversation

PixelboysTM
Copy link

@PixelboysTM PixelboysTM commented Nov 13, 2024

We are able to detect valid plugins and call their init method. pumpkin_plugin contains a sample plugin.
Functionality needs to be documented.

More to come. Open for discussion.

Description

Testing

Checklist

Things need to be done before this Pull Request can be merged.

  • Test on all OSes
  • Provide a logging API to plugins
  • provide basic event handlers
  • Code does not produce any clippy warnings cargo clippy

We are able to detect valid plugins and call teir init method.
pumpkin_plugin contains a sample plugin.
Functinality needs to be documented.
@neeleshpoli
Copy link
Contributor

I came across Hyperlight and I think this might be the way to go for a plugin system.

Hyperlight is a lightweight Virtual Machine Manager (VMM) designed to be embedded within applications. It enables safe execution of untrusted code within micro virtual machines with very low latency and minimal overhead.

Visit the Hyperlight repo for more information.

Since a goal of the project is security, I think hyperlight could help safely load plugins and execute them. Looking at the README, it seems like Hyperlight is pretty easy to use and doesn't require unsafe rust. It should also be pretty easy to create a wrapper crate around hyperlight for plugins to use.

Drawbacks

Seems like this project is active and these drawbacks might not be valid over time.

  • Seems to be pretty new, only being released last week
  • No MacOS support
  • Only 64-bit support
  • And there could be more I am missing

@DataM0del
Copy link
Contributor

  • No MacOS support

It could be implemented, but with the MacOS hypervisor, you can only have 1 hypervisor running per process... If you don't want to click the link:

A guest is an operating system that runs on top of the virtual hardware. The operating system and processes that run the virtualized hardware are together called the host. Virtual hardware in the guest maps to specific resources on the host.

Each virtual machine corresponds to a process on the host. There can only be one virtual machine at a time per process; the virtual machine creates it with hv_vm_create(_:).

You could probably abuse this by spawning a process per plugin, but I don't feel right when I hear "spawn a process for each plugin so we use a hypervisor to virtualize the plugin"...

@Snowiiii
Copy link
Owner

Snowiiii commented Nov 14, 2024

Hello. I'm against using an .zip or similar archives to package a Plugin with multiple binaries for all Operating Systems.

  1. This results in not needed Bloat for the User.
  2. This will limit Operating Support. (Pumpkin does also support more than Windows, macOS and Linux, We currently only limited by tokio afaik)

The Solution i would use is to just put in the compiled Plugin binaries into the Plugins folder and then Check if the current Platform can load these Plugins.

To address @neeleshpoli

Since a goal of the project is security, I think hyperlight could help safely load plugins and execute them. Looking at the README, it seems like Hyperlight is pretty easy to use and doesn't require unsafe rust. It should also be pretty easy to create a wrapper crate around hyperlight for plugins to use.

Yes, Not using a Runtime does give Plugins developers more access to the machine, Which can results in some Security concerns. Hover there are ways to limit the permissions. One example would be to use seccomp under Linux. See https://users.rust-lang.org/t/is-it-possible-to-limit-file-system-access-to-dependencies/44284/9 for details.
You should also consider that one goal (if not the Main goal) of Pumpkin is to be Lightweight and Fast. Which is easier done when not using any Runtime

@PixelboysTM
Copy link
Author

In reply to @Snowiiii

Hello. I'm against using an .zip or similar archives to package a Plugin with multiple binaries for all Operating Systems.

My Idea, with one universal archive, was to remove complexity on the using site of plugins. Because in my mind, the one developing Plugins is more experienced with what is needed for different architectures to work, then the Kid randomly downloading TNT Pranks with their friends.

I see how it makes the final plugin more bloated, though.
Another benefit of using an archive in my opinion is to be able to package additional assets within the plugin. For example, configs, lang files or crafting recipes etc. Minecrafts resource packs are heavily based around individual files.

Regarding a microVM, I took a brief look at the proposed package but very quickly came to the resolution, that it only complicates a streamlined process and adds indirection, removing the benefit of rusts powerful type system and borrow checker.

I am also of the opinion that it is not our responsibility to ensure others can't expose a plugin. I agree that we should put measures in place for hardening the process, but never should we sacrifice other aspects of a fast and easy to use API for that.

@suprohub
Copy link
Contributor

Why not just use .rlib

@neeleshpoli
Copy link
Contributor

neeleshpoli commented Nov 15, 2024

Why not just use .rlib

Doesn't rlib have an unstable ABI? Also, it seems like it's very difficult to use .rlib files directly in code

@DataM0del
Copy link
Contributor

DataM0del commented Nov 15, 2024

Why not lock out the pr*priet*ry plugins and execute the source code instead of the binary?

@suprohub
Copy link
Contributor

I think will be good use all options:
Use dll and other for supporting other languages
Use .rlib (compiled rust libs, can be used as dependency
Use source code

@PixelboysTM
Copy link
Author

.rlib can't be used as it being a statically link library type as far as I am aware

@PixelboysTM
Copy link
Author

PixelboysTM commented Nov 15, 2024

Why not lock out the pr*priet*ry plugins and execute the source code instead of the binary?
What do you mean by that @suprohub

@lokka30
Copy link
Contributor

lokka30 commented Nov 17, 2024

Why not lock out the prprietry plugins and execute the source code instead of the binary?

Plugin developers will just write a small source-available part of the code purely to load their proprietary binary that does the bulk of the plugin's work :(

I don't think there's much we can do to avoid people from writing proprietary plugins

@neeleshpoli
Copy link
Contributor

execute the source code

This is not a good idea, since plugins need to be compiled on every server now before they are executed (assuming the plugins are coded in rust). This means every server owner would need to install rust and cargo, and the necessary toolchains. This introduces a level of complexity that server owners shouldn't have to deal with.

I understand you might dislike proprietary software, but ultimately, it's the decision of the plugin developer to make it open source or proprietary and the decision of server owners on whether they trust a proprietary plugin or not.

@DataM0del
Copy link
Contributor

Why not lock out the pr_priet_ry plugins and execute the source code instead of the binary?

Plugin developers will just write a small source-available part of the code purely to load their proprietary binary that does the bulk of the plugin's work :(

I don't think there's much we can do to avoid people from writing proprietary plugins

Solution:
Ditch MIT license and use AGPLv3. Chase down the proprietary plugins (because they have to link with it somehow, AGPL instead of GPL because you could just have an Open Source GPL v3 program that communicates through the network and with AGPL it would be illegal, whereas with GPL it would be okay).
Make it so you can't run binaries on the system in these plugins by running it in something like Firejail.
You've probably solved 20% of the problem already. Now, you could just implement a VM in Rust, but that would be complex, as this language isn't as flexable as JS or Luau.

1,000 more Open Source things instead of those 1,000 others just being proprietary plugins.

@DataM0del
Copy link
Contributor

execute the source code

This is not a good idea, since plugins need to be compiled on every server now before they are executed (assuming the plugins are coded in rust). This means every server owner would need to install rust and cargo, and the necessary toolchains. This introduces a level of complexity that server owners shouldn't have to deal with.

I understand you might dislike proprietary software, but ultimately, it's the decision of the plugin developer to make it open source or proprietary and the decision of server owners on whether they trust a proprietary plugin or not.

Actually, you could still use binaries anyways but just change the license to AGPL and it would be illegal under US copyright to make it proprietary, can't just open source a "proxy" plugin that allows you to interact with the plugin interface under AGPL and then use it in a proprietary plugin, as you have to either keep it AGPL or stop interacting with it entirely.

@lokka30
Copy link
Contributor

lokka30 commented Nov 17, 2024

Actually, you could still use binaries anyways but just change the license to AGPL and it would be illegal under US copyright to make it proprietary, can't just open source a "proxy" plugin that allows you to interact with the plugin interface under AGPL and then use it in a proprietary plugin, as you have to either keep it AGPL or stop interacting with it entirely.

I don't think we have the necessary resources to chase down copyright issues. Even Bukkit is GPL yet plenty of plugins developed for it are closed source, DRM, etc. Bukkit was basically the only server people were using back then, and still chose not to fight plugins clearly breaching GPL.

AGPL in particular is a fantastic license though it won't work for Pumpkin. To my understanding it would require server owners to share the source code of any changes they made to Pumpkin + all of the plugins they're using. It'll scare away big servers from using Pumpkin, and the rest will just ignore the license completely.

This is not a good idea, since plugins need to be compiled on every server now before they are executed (assuming the plugins are coded in rust). This means every server owner would need to install rust and cargo, and the necessary toolchains. This introduces a level of complexity that server owners shouldn't have to deal with.

+1. The only time I would agree with a source-distribution solution would be with scripting languages, e.g., Lua, which are always distributed in source form anyways

I understand you might dislike proprietary software, but ultimately, it's the decision of the plugin developer to make it open source or proprietary and the decision of server owners on whether they trust a proprietary plugin or not.

This is why I'm all for some type of plugin system that runs in a VM. Gives the server admins some safety from some malicious or poorly written plugins. There have also been cases where plugins claim git repo is their source code but actually distributes a malicious binary with slightly altered code.

@DataM0del
Copy link
Contributor

AGPL in particular is a fantastic license though it won't work for Pumpkin. To my understanding it would require server owners to share the source code of any changes they made to Pumpkin + all of the plugins they're using. It'll scare away big servers from using Pumpkin, and the rest will just ignore the license completely.

GPL worked for Bukkit, GPL could work for us, but the only difference between AGPL and GPL is that AGPL counts network use as distribution. Also, I don't think plugins are counted as modifications.
I contacted my legal expert (aka ChatGPT 💀), and it seems like you would only have to disclose the plugin's source code if it uses the server internals instead of just its public API, and you don't have to list the plugins you're using.

Under the AGPL v3 (Affero General Public License version 3), the key requirement is that if you modify the software and make it available to users over a network, you must make the source code of your modified version available to those users. However, whether this includes disclosing a list of plugins you use depends on a few factors.

Plugins and the AGPL v3 License

  • Standalone Plugins: If the plugins you are using are independent pieces of software (i.e., they don't derive from or modify the AGPL-covered server code but merely interact with it using well-defined APIs), then they would generally not be considered "modifications" of the AGPL software. In this case, you would not be obligated to disclose their source code or even the list of plugins you are using.

  • Derivatives or Modified Works: If the plugins are tightly integrated to the point where they are considered derivative works of the server (e.g., they rely on the server’s internals rather than just its public API), then they might be subject to the AGPL. In that case, you would likely be required to disclose the source code of these plugins if you distribute or provide access to the server over a network.

Disclosure of Plugin List

The AGPL v3 itself doesn't explicitly require you to disclose a list of all the plugins you are using; rather, it focuses on source code availability. If the plugins are independent and not derivative works, simply using them with your server would not typically trigger an obligation to disclose their existence.

However, if the plugins are considered an essential part of the software as you are offering it (e.g., if they modify core functionality or are tightly integrated), users could argue they have a right to know which plugins are involved since it might affect their ability to access the complete, corresponding source code of what they are interacting with.

Practical Considerations

If you are concerned about compliance:

  • Document your plugin architecture clearly, showing how plugins interact with your server. This can help demonstrate that they are independent modules rather than derivative works.
  • Consult a legal expert to ensure that your specific use case does not inadvertently violate the AGPL v3 requirements, especially if your server’s functionality is heavily dependent on plugins.

In most common cases where plugins are developed independently and communicate via APIs, listing them wouldn't be required under AGPL v3.

@lokka30
Copy link
Contributor

lokka30 commented Nov 17, 2024

being FOSS definitely worked great for Bukkit – but I don't think the GPL's legal requirements are being adhered to, so it may as well be effectively MIT

@Snowiiii
Copy link
Owner

Is there a discussion about forbidding closed sourced Plugins ?. Or what is this licensing talk about ?. Plugin developers should be able to decide their own if they want to publish the source code or not. I have also high interest making a Plugin Marketplace for Pumpkin, There developers can Publish free but also paid plugins. For Paid plugins it only makes sense to have them closed source

@DataM0del
Copy link
Contributor

Is there a discussion about forbidding closed sourced Plugins ?. Or what is this licensing talk about ?. Plugin developers should be able to decide their own if they want to publish the source code or not. I have also high interest making a Plugin Marketplace for Pumpkin, There developers can Publish free but also paid plugins. For Paid plugins it only makes sense to have them closed source

Pretty much forbidding closed source plugins.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

6 participants