[Home] [Downloads] [Search] [Help/forum]

Register forum user name Search FAQ

Gammon Forum

[Folder]  Entire forum
-> [Folder]  MUSHclient
. -> [Folder]  General
. . -> [Subject]  More relaxed Lua sandbox / security tips

More relaxed Lua sandbox / security tips

This subject is now closed.     [Refresh] Refresh page

Posted by Nick Gammon   Australia  (23,006 posts)  [Biography] bio   Forum Administrator
Date Sat 14 Aug 2010 09:57 PM (UTC)

Amended on Tue 21 Aug 2018 12:00 AM (UTC) by Nick Gammon

This page can be quickly reached from the link: http://www.gammon.com.au/security

The Lua sandbox - and trusting plugins

After lengthy discussion[1] the "Lua sandbox" in MUSHclient is going to be made less intrusive, from version 4.57 onwards.

The sandbox was intended to make it harder for malicious scripts to do harmful things to your PC (like, create viruses, delete files, etc.). However the problem with it has been twofold:

  • It only affects Lua, so people could, if they wanted, do those things in other script languages, like VBscript.

  • It made it hard for script-writers to do useful things (like read configuration files), because the sandbox would stop them.

The changes in version 4.57 will only affect new installations of MUSHclient. The instructions below describe how to make similar changes to existing installations.

How to disable the Lua sandbox

  • Open MUSHclient and go to the File menu -> Global Preferences (Ctrl+Alt+G)

  • Click on the Lua tab

  • In the big box (Preliminary code) RH-click, and choose "Select All".

  • Hit the Delete key to delete everything.

  • Type in at least two hyphens (which is a comment in Lua) otherwise MUSHclient will put the default sandbox back. You could enter, for example:

    -- Empty sandbox

  • Check the checkbox "Allow DLLs to be loaded"

  • Click OK to save the changes

Your changes should look like this:

How do you know who to trust?

With the sandbox disabled you are slightly at more risk from malicious plugins. As I said earlier, anyone who wants to can simply not use Lua, so the risk isn't much greater.

However, regardless of the script language, there are some steps you can take to stay reasonably safe.

The main rule is to only install plugins from trusted plugin-writers.

Trusted plugins would generally meet one or more of the following conditions:

  • Plugins distributed with MUSHclient itself (if MUSHclient was downloaded from the mushclient.com web site)

  • Plugins distributed from my GitHub plugins site:


  • Plugins downloaded from the plugins page on this site:


  • Plugins mentioned at the top of the plugins forum page:


  • Plugins suggested by your MUD on their main web pages (not just a forum page but a page operated by the MUD themselves). Presumably they are only recommending trusted plugins.

  • Plugins found on this forum, by a forum poster who has made many (like, over 100) postings. Such forum posters are generally trusted and well-regarded. Each forum posting tells you how many posts that person has made, like this:

    In this case we see that Blainer has made 191 posts, so he can probably be trusted.

  • As a double-check, go to the main forum page (http://mushclient.com/forum/), scroll down to the bottom, and check when that person joined the forum. For example:

    We see that Blainer joined the forum over a year ago.

    Only people who have made more than 100 posts show up on that list. Another approach is to click on their "bio" (as in the screenshot above) and check when they joined the forum. So someone who had made 80 posts, and joined over a year ago, is probably safe to trust.

  • Posts by Nick Gammon (the author of MUSHclient) (that is, me). Such posts pass the previous two tests anyway, as I am a frequent poster on the forum.

Plugins to be wary of

If someone suggests you install something that looks like the following, I would be very wary:

  • An in-game whisper to download some "new cool feature" that does not send you to the mushclient.com forum or web site

  • Anything that needs you to run an executable (ie. MyGreatMapper.exe). Note that plugins are XML files (eg. mapper.xml) not executable files.

  • Anything that includes a DLL file (eg. mapper.dll). DLLs can execute arbitrary code (eg. viruses).

  • Anything that is supplied in "pre-compiled" form (eg. Lua bytecode) which is not possible to inspect and check for malicious activities, such as deleting files, sending files over the Internet, and so on.

  • Anything recommended by someone who joined the forum recently (like, in the last few days)

  • Anything recommended by someone who has only made a handful of forum postings.

  • Anything recommended by someone who does not exist on this forum here at all.

  • Anything from someone claiming to be someone trusted (eg. Nick Gammon) but which takes you to some other web site than this one.

  • Anything that requires you to login to some external web site (to "verify" who you are).

  • Be cautious of plugins which are inside .zip files. In particular you should only need to unzip the archive, not automatically run anything inside it.

Note that some plugin writers (Twisol is an example) have developed a plugin directory structure which uses .zip files.

If a trusted plugin writer (who meets the conditions earlier in this post) needs you to unzip a .zip file, or use a .dll file, this should be OK.

The use of .zip files, .dll files, or .exe files is a "red flag" for unknown plugin writers.

This web site (http://mushclient.com/) never asks people to login to "verify" their account information. Either you can login to the forum (http://mushclient.com/forum/) or you can't. There is no other verification procedure.

Sandbox discussion

1. http://mushclient.com/forum/?id=10497

- Nick Gammon

www.gammon.com.au, www.mushclient.com
[Go to top] top

Posted by Nick Gammon   Australia  (23,006 posts)  [Biography] bio   Forum Administrator
Date Reply #1 on Sat 14 Aug 2010 10:02 PM (UTC)

Amended on Sat 04 Sep 2010 09:36 PM (UTC) by Nick Gammon

Original sandbox

If you want to keep the existing sandbox functionality, below is how the sandbox looked in versions 4.56 and below:

trust_all_worlds = false    -- change to true to trust all the worlds
trust_all_plugins = false   -- change to true to trust all the plugins
warn_if_not_trusted = false -- change to true to show warnings


-- Lua initialization (sandbox) --> please read comments carefully.

-- Default initialization supplied with version 3.80.

Use this to create a "sandbox" for safe execution of non-trusted scripts.

If you only run your own scripts or plugins then you may not need this.

The code in this area is executed after each Lua script space is created
but before any of your scripts are done. This can be used to initialise things
(eg. load DLLs, load files, set up variables) or to disable things as shown below.

By setting a function name to nil you effectively make it unavailable.

You can remove some functions from a library rather than all of them, eg.

  os.execute = nil  -- no operating system calls
  os.remove = nil   -- no deleting files
  os.rename = nil   -- no renaming files

This script will automatically be replaced if you completely delete it from
the Global Preferences, and restart MUSHclient. To avoid this, leave a comment
in (if you don't want any further action taken).


-- Example sandbox --

function MakeSandbox ()

  local function ReportDisabled (pkg, func)
     return function ()
       error (string.format (
        "Function '%s.%s' disabled in Lua sandbox - see MUSHclient global preferences",
        pkg, func), 2)
       end -- function
  end -- ReportDisabled 

  package.loadlib = ReportDisabled  ("package", "loadlib") -- disable loadlib function
  package.loaders [3] = nil  -- disable DLL loader
  package.loaders [4] = nil  -- disable all-in-one loader

  for k, v in pairs (io) do
    if type (v) == "function" then
      io [k] = ReportDisabled ("io", k)
    end -- type is function
  end -- for

  local orig_os = os -- so we know names of disabled ones

  -- replace 'os' table with one containing only safe functions
  os = {
       date = os.date,
       time = os.time, 
       setlocale = os.setlocale,
       clock = os.clock, 
       difftime = os.difftime,

  for k, v in pairs (orig_os) do
    if not os [k] and type (v) == "function" then
      os [k] = ReportDisabled ("os", k)
    end -- not still active
  end -- for

   if warn_if_not_trusted then
     ColourNote ("yellow", "black", 
                 "Lua sandbox created, some functions disabled.")
   end -- if warn_if_not_trusted

end -- end of function MakeSandbox

-- default is to sandbox everything --

-- To trust individual worlds or plugins, add them to the lists below.
-- To find your current world ID, do this: /print (GetWorldID ())
-- Plugin IDs are mentioned near the start of every plugin.

-- You can limit the behaviour to specific worlds, or specific plugins
-- by doing something like this:


  -- World IDs of worlds we trust - replace with your world IDs
  --    (and remove comment from start of line)

  local trusted_worlds = {
 --    ["a4a1cc1801787ba88cd84f3a"] = true,  -- example world A
 --    ["cdc8552d1b251e449b874b9a"] = true,  -- example world B
 --    ["1ec5aac3265e472b97f0c103"] = true,  -- example world C
      }  -- end of trusted_worlds 

  -- Plugin IDs of plugins we trust - add your plugins to the table

  local trusted_plugins = {
     [""] = "",            -- trust main script (ie. if no plugin running)
     ["03ca99c4e98d2a3e6d655c7d"] = "Chat",  
     ["982581e59ab42844527eec80"] = "Random_Socials", 
     ["4a267cd69ba59b5ecefe42d8"] = "Installer_sumcheck",  
     ["83beba4e37b3d0e7f63cedbc"] = "Reconnecter",   
     }  -- end of trusted_plugins 

  -- check worlds 
  if not trust_all_worlds then                
    if not trusted_worlds [GetWorldID ()] then
       if warn_if_not_trusted  then
         ColourNote ("yellow", "black", "Untrusted world " .. WorldName () .. 
                     ", ID: " .. GetWorldID ())
       end -- if warn_if_not_trusted
       MakeSandbox ()
    end -- not trusted world or plugin 
  end -- not trusting all worlds

  -- check plugins - check name *and* plugin ID
  if not trust_all_plugins then
    if trusted_plugins [GetPluginID ()] ~= GetPluginName () then
       if warn_if_not_trusted  then
         ColourNote ("yellow", "black", "Untrusted plugin " .. GetPluginName () .. 
                     ", ID: " .. GetPluginID ())
       end -- if warn_if_not_trusted 
       MakeSandbox ()
    end -- not trusted world or plugin
  end -- if not trusting all plugins

end -- local block

-- warn if we can't load DLLs (checkbox might be unchecked)
if not package.loadlib and warn_if_not_trusted  then
   local by_this_plugin = ""
   if GetPluginID () ~= "" then
     by_this_plugin = " by this plugin"
   end -- this is a plugin
   ColourNote ("yellow", "black", 
               "Loading of DLLs" .. by_this_plugin .. " is disabled.")
end -- if

Also "Allow DLLs to be loaded" was not checked.

The original sandbox is now supplied in version 4.60 onwards as "sandbox.lua" so just add this line to the Global Preferences -> Lua sandbox to revert to the original behaviour:

require "sandbox"

- Nick Gammon

www.gammon.com.au, www.mushclient.com
[Go to top] top

Posted by Nick Gammon   Australia  (23,006 posts)  [Biography] bio   Forum Administrator
Date Reply #2 on Tue 17 Aug 2010 05:08 AM (UTC)

Amended on Sat 04 Sep 2010 09:49 PM (UTC) by Nick Gammon

A useful thing to put into your Lua sandbox is the following:

-- Put Lua initialization code (eg. sandbox) here.
-- Possible sandbox, and security tips: http://www.gammon.com.au/security

if GetPluginID () == "" then
   ColourNote ("gray", "", "Initializing main world script")
  ColourNote ("gray", "", string.format ("Loading plugin '%s' (%s) version %0.2f",
    GetPluginInfo ( GetPluginID (), 7),
    GetPluginInfo ( GetPluginID (), 1),
    GetPluginInfo ( GetPluginID (), 19)))
end -- if

What that does is remind you of how to reach this page, and also displays a message when any Lua plugin loads (because Lua executes the sandbox). It also lets you know when you are reloading the main script file (if it is written in Lua).

The above is supplied in MUSHclient 4.60 onwards as the module show_loaded.lua, so just add this line to the Global Preferences -> Lua sandbox to have it display when each plugin loads:

require "show_loaded"

You might see something like this as the world loads:

Loading plugin '4d167d47cac26fb36e161e48' (AFK_timer) version 1.00
Loading plugin '03ca99c4e98d2a3e6d655c7d' (Chat) version 1.00
Initializing main world script

You could also add a "require" for things you like to have available, eg.

require "tprint"
require "commas"

- Nick Gammon

www.gammon.com.au, www.mushclient.com
[Go to top] top

Posted by Nick Gammon   Australia  (23,006 posts)  [Biography] bio   Forum Administrator
Date Reply #3 on Wed 01 Sep 2010 03:47 AM (UTC)
The other thing you can put in your custom sandbox is to disable things you might be worried about.

For example, from version 4.60 onwards there is a utils.shellexecute function that lets scripts execute arbitrary Windows commands.

If you are loading plugins that you don't necessarily trust, you can disable that by putting this into the sandbox:

utils.shellexecute = nil

That replaces that slightly dangerous function with nil, which effectively deletes it from the script space.

You can do the same for any other function you don't particularly need or want scripts to be able to execute.

- Nick Gammon

www.gammon.com.au, www.mushclient.com
[Go to top] top

The dates and times for posts above are shown in Universal Co-ordinated Time (UTC).

To show them in your local time you can join the forum, and then set the 'time correction' field in your profile to the number of hours difference between your location and UTC time.


This subject is now closed.     [Refresh] Refresh page

Go to topic:           Search the forum

[Go to top] top

Quick links: MUSHclient. MUSHclient help. Forum shortcuts. Posting templates. Lua modules. Lua documentation.

Information and images on this site are licensed under the Creative Commons Attribution 3.0 Australia License unless stated otherwise.


Written by Nick Gammon - 5K   profile for Nick Gammon on Stack Exchange, a network of free, community-driven Q&A sites   Marriage equality

Comments to: Gammon Software support
[RH click to get RSS URL] Forum RSS feed ( https://gammon.com.au/rss/forum.xml )

[Best viewed with any browser - 2K]    [Hosted at HostDash]