implement [lua]name=, fixes #3381
This commit is contained in:
parent
50d94b3388
commit
eba882b957
6 changed files with 20 additions and 19 deletions
|
@ -267,7 +267,8 @@ end
|
|||
|
||||
function wml_actions.lua(cfg)
|
||||
cfg = wml.shallow_literal(cfg)
|
||||
local bytecode, message = load(cfg.code or "")
|
||||
--fixme untested
|
||||
local bytecode, message = load(cfg.code or "", cfg.name or "")
|
||||
if not bytecode then error("~lua:" .. message, 0) end
|
||||
bytecode(wml.get_child(cfg, "args"))
|
||||
end
|
||||
|
|
|
@ -394,7 +394,7 @@ bool game_launcher::init_lua_script()
|
|||
|
||||
std::cerr << "\nRunning lua script: " << *cmdline_opts_.script_file << std::endl;
|
||||
|
||||
plugins_manager::get()->get_kernel_base()->run(full_script.c_str());
|
||||
plugins_manager::get()->get_kernel_base()->run(full_script.c_str(), *cmdline_opts_.script_file);
|
||||
} else {
|
||||
std::cerr << "Encountered failure when opening script '" << *cmdline_opts_.script_file << "'\n";
|
||||
error = true;
|
||||
|
|
|
@ -670,10 +670,10 @@ bool lua_kernel_base::protected_call(int nArgs, int nRets)
|
|||
return this->protected_call(nArgs, nRets, eh);
|
||||
}
|
||||
|
||||
bool lua_kernel_base::load_string(char const * prog)
|
||||
bool lua_kernel_base::load_string(char const * prog, const std::string& name)
|
||||
{
|
||||
error_handler eh = std::bind(&lua_kernel_base::log_error, this, _1, _2 );
|
||||
return this->load_string(prog, eh);
|
||||
return this->load_string(prog, name, eh);
|
||||
}
|
||||
|
||||
bool lua_kernel_base::protected_call(int nArgs, int nRets, error_handler e_h)
|
||||
|
@ -716,11 +716,11 @@ bool lua_kernel_base::protected_call(lua_State * L, int nArgs, int nRets, error_
|
|||
return true;
|
||||
}
|
||||
|
||||
bool lua_kernel_base::load_string(char const * prog, error_handler e_h)
|
||||
bool lua_kernel_base::load_string(char const * prog, const std::string& name, error_handler e_h)
|
||||
{
|
||||
// pass 't' to prevent loading bytecode which is unsafe and can be used to escape the sandbox.
|
||||
// todo: maybe allow a 'name' parameter to give better error messages.
|
||||
int errcode = luaL_loadbufferx(mState, prog, strlen(prog), /*name*/ prog, "t");
|
||||
int errcode = luaL_loadbufferx(mState, prog, strlen(prog), name.empty() ? name.c_str() : prog, "t");
|
||||
if (errcode != LUA_OK) {
|
||||
char const * msg = lua_tostring(mState, -1);
|
||||
std::string message = msg ? msg : "null string";
|
||||
|
@ -753,24 +753,24 @@ void lua_kernel_base::run_lua_tag(const config& cfg)
|
|||
luaW_pushconfig(this->mState, args);
|
||||
++nArgs;
|
||||
}
|
||||
this->run(cfg["code"].str().c_str(), nArgs);
|
||||
this->run(cfg["code"].str().c_str(), cfg["name"].str(), nArgs);
|
||||
}
|
||||
// Call load_string and protected call. Make them throw exceptions.
|
||||
//
|
||||
void lua_kernel_base::throwing_run(const char * prog, int nArgs)
|
||||
void lua_kernel_base::throwing_run(const char * prog, const std::string& name, int nArgs)
|
||||
{
|
||||
cmd_log_ << "$ " << prog << "\n";
|
||||
error_handler eh = std::bind(&lua_kernel_base::throw_exception, this, _1, _2 );
|
||||
this->load_string(prog, eh);
|
||||
this->load_string(prog, name, eh);
|
||||
lua_insert(mState, -nArgs - 1);
|
||||
this->protected_call(nArgs, 0, eh);
|
||||
}
|
||||
|
||||
// Do a throwing run, but if we catch a lua_error, reformat it with signature for this function and log it.
|
||||
void lua_kernel_base::run(const char * prog, int nArgs)
|
||||
void lua_kernel_base::run(const char * prog, const std::string& name, int nArgs)
|
||||
{
|
||||
try {
|
||||
this->throwing_run(prog, nArgs);
|
||||
this->throwing_run(prog, name, nArgs);
|
||||
} catch (const game::lua_error & e) {
|
||||
cmd_log_ << e.what() << "\n";
|
||||
lua_kernel_base::log_error(e.what(), "In function lua_kernel::run()");
|
||||
|
@ -787,9 +787,9 @@ void lua_kernel_base::interactive_run(char const * prog) {
|
|||
|
||||
try {
|
||||
// Try to load the experiment without syntax errors
|
||||
this->load_string(experiment.c_str(), eh);
|
||||
this->load_string(experiment.c_str(), "interactive", eh);
|
||||
} catch (const game::lua_error &) {
|
||||
this->throwing_run(prog, 0); // Since it failed, fall back to the usual throwing_run, on the original input.
|
||||
this->throwing_run(prog, "interactive", 0); // Since it failed, fall back to the usual throwing_run, on the original input.
|
||||
return;
|
||||
}
|
||||
// experiment succeeded, now run but log normally.
|
||||
|
|
|
@ -32,10 +32,10 @@ public:
|
|||
void run_lua_tag(const config& cfg);
|
||||
|
||||
/** Runs a plain script. Doesn't throw lua_error.*/
|
||||
void run(char const *prog, int nArgs = 0);
|
||||
void run(char const *prog, const std::string& name, int nArgs = 0);
|
||||
|
||||
/** Runs a plain script, but reports errors by throwing lua_error.*/
|
||||
void throwing_run(char const * prog, int nArgs);
|
||||
void throwing_run(char const * prog, const std::string& name, int nArgs);
|
||||
|
||||
/** Tests if a program resolves to an expression, and pretty prints it if it is, otherwise it runs it normally. Throws exceptions.*/
|
||||
void interactive_run(char const * prog);
|
||||
|
@ -122,10 +122,10 @@ protected:
|
|||
// Execute a protected call, taking a lua_State as argument. For functions pushed into the lua environment, this version should be used, or the function cannot be used by coroutines without segfaulting (since they have a different lua_State pointer). This version is called by the above version.
|
||||
static bool protected_call(lua_State * L, int nArgs, int nRets, error_handler);
|
||||
// Load a string onto the stack as a function. Returns true if successful, error handler is called if not.
|
||||
bool load_string(char const * prog, error_handler);
|
||||
bool load_string(char const * prog, const std::string& name, error_handler);
|
||||
|
||||
virtual bool protected_call(int nArgs, int nRets); // select default error handler polymorphically
|
||||
virtual bool load_string(char const * prog); // select default error handler polymorphically
|
||||
virtual bool load_string(char const * prog, const std::string& name); // select default error handler polymorphically
|
||||
|
||||
// dofile (using lua_fileops)
|
||||
int intf_dofile(lua_State * L);
|
||||
|
|
|
@ -234,7 +234,7 @@ mapgen_lua_kernel::mapgen_lua_kernel()
|
|||
|
||||
void mapgen_lua_kernel::run_generator(const char * prog, const config & generator)
|
||||
{
|
||||
load_string(prog, std::bind(&lua_kernel_base::throw_exception, this, _1, _2));
|
||||
load_string(prog, "", std::bind(&lua_kernel_base::throw_exception, this, _1, _2));
|
||||
luaW_pushconfig(mState, generator);
|
||||
protected_call(1, 1, std::bind(&lua_kernel_base::throw_exception, this, _1, _2));
|
||||
}
|
||||
|
|
|
@ -556,7 +556,7 @@ SYNCED_COMMAND_HANDLER_FUNCTION(debug_lua, child, use_undo, /*show*/, /*error_ha
|
|||
resources::undo_stack->clear();
|
||||
}
|
||||
debug_cmd_notification("lua");
|
||||
resources::lua_kernel->run(child["code"].str().c_str());
|
||||
resources::lua_kernel->run(child["code"].str().c_str(), "debug command");
|
||||
resources::controller->pump().flush_messages();
|
||||
|
||||
return true;
|
||||
|
|
Loading…
Add table
Reference in a new issue