LMCAS
Lamina Computer Algebra System
载入中...
搜索中...
未找到
lmmc_lifecycle.cpp
浏览该文件的文档.
2
3#include "lmmc/init.h"
4
5#include <cstdint>
6#include <exception>
7
8#ifdef _WIN32
9#include <windows.h>
10#endif
11
12namespace LMCAS::detail {
13namespace {
14
15#ifdef _WIN32
16/**
17 * @brief 使用原生 FLS,在 LMMP/LMMC 线程状态有效时清理,兼容内部测试链接。
18 * @note 可执行文件的 C++ TLS 析构可能晚于依赖的 MinGW DLL 仿真 TLS 销毁。
19 */
20// FlsFree can invoke callbacks for other threads. Only thread exit or the
21// unloading thread may release its lease; live foreign threads are reclaimed
22// by process exit. Explicit unload requires all other CAS threads to be joined.
23void CALLBACK release_lmmc_lifecycle(void* owner) {
24 if (reinterpret_cast<std::uintptr_t>(owner) == GetCurrentThreadId() &&
25 lmmc_deinit() != LMMC_STATUS_OK) {
26 std::terminate();
27 }
28}
29
30class LmmcLifecycleSlot final {
31public:
32 LmmcLifecycleSlot() : index_(FlsAlloc(release_lmmc_lifecycle)) {
33 if (index_ == FLS_OUT_OF_INDEXES) {
34 std::terminate();
35 }
36 }
37
38 ~LmmcLifecycleSlot() {
39 if (void* owner = FlsGetValue(index_)) {
40 if (!FlsSetValue(index_, nullptr)) {
41 std::terminate();
42 }
43 release_lmmc_lifecycle(owner);
44 }
45 if (!FlsFree(index_)) {
46 std::terminate();
47 }
48 }
49
50 DWORD index() const noexcept { return index_; }
51
52 LmmcLifecycleSlot(const LmmcLifecycleSlot&) = delete;
53 LmmcLifecycleSlot& operator=(const LmmcLifecycleSlot&) = delete;
54
55private:
56 DWORD index_;
57};
58#else
59class LmmcLifecycle final {
60public:
62 if (lmmc_init() != LMMC_STATUS_OK) {
63 std::terminate();
64 }
65 }
66
68 if (lmmc_deinit() != LMMC_STATUS_OK) {
69 std::terminate();
70 }
71 }
72
73 LmmcLifecycle(const LmmcLifecycle&) = delete;
75};
76#endif
77
78}
79
80void ensure_lmmc_lifecycle() noexcept {
81#ifdef _WIN32
82 static LmmcLifecycleSlot slot;
83 if (FlsGetValue(slot.index())) {
84 return;
85 }
86 if (lmmc_init() != LMMC_STATUS_OK) {
87 std::terminate();
88 }
89 void* owner = reinterpret_cast<void*>(static_cast<std::uintptr_t>(GetCurrentThreadId()));
90 if (!FlsSetValue(slot.index(), owner)) {
91 if (lmmc_deinit() != LMMC_STATUS_OK) {
92 std::terminate();
93 }
94 std::terminate();
95 }
96#else
97 static thread_local LmmcLifecycle lifecycle;
98 (void)lifecycle;
99#endif
100}
101
102}
LmmcLifecycle & operator=(const LmmcLifecycle &)=delete
多元 Hensel 提升(单变量步)
void ensure_lmmc_lifecycle() noexcept