ThePhD / sol2

Sol3 (sol2 v3.0) - a C++ <-> Lua API wrapper with advanced features and top notch performance - is here, and it's great! Documentation:
http://sol2.rtfd.io/
MIT License
4.06k stars 493 forks source link

C++ Exception Handling broke in 3.3.0 #1508

Open pfirsich opened 1 year ago

pfirsich commented 1 year ago
#include <cstdio>

#define SOL_ALL_SAFETIES_ON 1
#include <sol/sol.hpp>

class MyException : public std::runtime_error {
public:
    template <typename Msg>
    explicit MyException(Msg&& msg)
        : std::runtime_error(std::forward<Msg>(msg))
    {
    }
};

int solExceptionHandler(lua_State* L, sol::optional<const std::exception&> exc, sol::string_view desc)
{
    if (exc) {
        std::fprintf(stderr, "Exception: %s\n", exc->what());
    } else {
        std::string s(desc);
        std::fprintf(stderr, "Error: %s\n", s.c_str());
    }
    std::exit(1);
    return sol::stack::push(L, desc);
}

int main()
{
    sol::state lua;
    lua.set_exception_handler(solExceptionHandler);
    lua["throw"] = [](std::string msg) { throw MyException(msg); };
    lua.do_string("throw(\"Foobar\")");
}

With 3.2.2 this produces the following output:

Error: Foobar

With 3.3.0 the output is this instead:

[sol2] An error occurred and has been passed to an error handler: sol: runtime error: C++ exception
terminate called after throwing an instance of 'sol::error'
  what():  sol: runtime error: C++ exception
Aborted (core dumped)

This looks like a bug to me. Also is there a workaround to get the exception.what() string in 3.3.0?

Also for some reason the SOL_VERSION_STRING is "3.5.0" for 3.2.2 and "3.2.3" for 3.3.0. That is very confusing to say the least. I honestly think this might be worth re-releasing them just for that version string fix alone.

roman-orekhov commented 1 year ago

I get "Exception: Foobar" in both debug and release builds of branch develop.

pfirsich commented 1 year ago

Sorry it took a while to respond, but when I tested this again, I saw even weirder behavior. In fact there was no output anymore! It just ignored that an exception was thrown.

I should have noted that I use LuaJIT. Maybe that has something to do with it? But even with LuaJIT this worked fine in v3.2.1. I made some tests in this repo: https://github.com/pfirsich/sol2_issue_1508 Note this only works on Linux and requires vcpkg for the LuaJIT dependency.

roman-orekhov commented 1 year ago

Have you read the docs regarding LuaJIT and exceptions? If you followed that to no avail, then this may help

pfirsich commented 1 year ago

I did read it, but frankly I did not understand it completely. I tried defining SOL_EXCEPTIONS_SAFE_PROPAGATION as well, but that made no difference in any of the three sol versions I tried. So I might be using it incorrectly, but especially considering that it worked in a previous version I think something broke still.

I actually saw the comment in #1386 you linked before, but I wasn't sure if it's the same and didn't want to use inofficial versions of sol2 for now. I guess this might be worth a try for someone that actually wants to debug this. I mostly want to report this regression. I only use exceptions to terminate the program essentially, so I have replaced it with an exit, so I don't need a fix soon.