diff options
Diffstat (limited to 'src')
| -rw-r--r-- | src/lanes.cpp | 51 |
1 files changed, 14 insertions, 37 deletions
diff --git a/src/lanes.cpp b/src/lanes.cpp index 28f95f6..cf443f2 100644 --- a/src/lanes.cpp +++ b/src/lanes.cpp | |||
| @@ -1736,55 +1736,32 @@ static const struct luaL_Reg lanes_functions[] = | |||
| 1736 | { nullptr, nullptr } | 1736 | { nullptr, nullptr } |
| 1737 | }; | 1737 | }; |
| 1738 | 1738 | ||
| 1739 | /* | ||
| 1740 | * One-time initializations | ||
| 1741 | * settings table it at position 1 on the stack | ||
| 1742 | * pushes an error string on the stack in case of problem | ||
| 1743 | */ | ||
| 1744 | static void init_once_LOCKED( void) | ||
| 1745 | { | ||
| 1746 | #if (defined PLATFORM_OSX) && (defined _UTILBINDTHREADTOCPU) | ||
| 1747 | chudInitialize(); | ||
| 1748 | #endif | ||
| 1749 | } | ||
| 1750 | |||
| 1751 | // ################################################################################################# | 1739 | // ################################################################################################# |
| 1752 | 1740 | ||
| 1753 | // we are C++20, the flags are default-initialized to 'clear' | ||
| 1754 | std::atomic_flag s_insideInit; | ||
| 1755 | std::atomic_flag s_initDone; | ||
| 1756 | |||
| 1757 | // upvalue 1: module name | 1741 | // upvalue 1: module name |
| 1758 | // upvalue 2: module table | 1742 | // upvalue 2: module table |
| 1759 | // param 1: settings table | 1743 | // param 1: settings table |
| 1760 | LUAG_FUNC(configure) | 1744 | LUAG_FUNC(configure) |
| 1761 | { | 1745 | { |
| 1746 | // start with one-time initializations. | ||
| 1747 | { | ||
| 1748 | // C++ guarantees that the static variable initialization is threadsafe. | ||
| 1749 | static auto _ = std::invoke( | ||
| 1750 | []() | ||
| 1751 | { | ||
| 1752 | #if (defined PLATFORM_OSX) && (defined _UTILBINDTHREADTOCPU) | ||
| 1753 | chudInitialize(); | ||
| 1754 | #endif | ||
| 1755 | return false; | ||
| 1756 | } | ||
| 1757 | ); | ||
| 1758 | } | ||
| 1759 | |||
| 1762 | Universe* U = universe_get(L); | 1760 | Universe* U = universe_get(L); |
| 1763 | bool const from_master_state{ U == nullptr }; | 1761 | bool const from_master_state{ U == nullptr }; |
| 1764 | char const* name = luaL_checkstring(L, lua_upvalueindex(1)); | 1762 | char const* name = luaL_checkstring(L, lua_upvalueindex(1)); |
| 1765 | ASSERT_L(lua_type(L, 1) == LUA_TTABLE); | 1763 | ASSERT_L(lua_type(L, 1) == LUA_TTABLE); |
| 1766 | 1764 | ||
| 1767 | /* | ||
| 1768 | ** Making one-time initializations. | ||
| 1769 | ** | ||
| 1770 | ** When the host application is single-threaded (and all threading happens via Lanes) | ||
| 1771 | ** there is no problem. But if the host is multithreaded, we need to lock around the | ||
| 1772 | ** initializations. | ||
| 1773 | */ | ||
| 1774 | if (s_insideInit.test_and_set()) | ||
| 1775 | { | ||
| 1776 | // blocks until flag value is no longer the one passed in parameter | ||
| 1777 | s_initDone.wait(false); | ||
| 1778 | } | ||
| 1779 | else | ||
| 1780 | { | ||
| 1781 | // we are the first to enter here, because s_insideInit was false. | ||
| 1782 | // and we are the only one, because it's now true. | ||
| 1783 | init_once_LOCKED(); | ||
| 1784 | std::ignore = s_initDone.test_and_set(); | ||
| 1785 | s_initDone.notify_all(); | ||
| 1786 | } | ||
| 1787 | |||
| 1788 | STACK_GROW(L, 4); | 1765 | STACK_GROW(L, 4); |
| 1789 | STACK_CHECK_START_ABS(L, 1); // settings | 1766 | STACK_CHECK_START_ABS(L, 1); // settings |
| 1790 | 1767 | ||
