Skip to content

Commit 9a62c3a

Browse files
committed
Fix crash related to unwind protect short circuiting
It seems relying on non-local static objects can cause memory issues, that are resolved by moving to use a local static objects instead. Fixes #244
1 parent c22dc9b commit 9a62c3a

File tree

2 files changed

+7
-6
lines changed

2 files changed

+7
-6
lines changed

NEWS.md

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,7 @@
11
# cpp11 (development version)
22

3+
* Fix crash related to unwind protect optimization (#244)
4+
35
# cpp11 0.4.0
46

57
## New Features

inst/include/cpp11/protect.hpp

Lines changed: 5 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -70,8 +70,6 @@ inline Rboolean& get_should_unwind_protect() {
7070
return should_unwind_protect[0];
7171
}
7272

73-
static Rboolean& should_unwind_protect = get_should_unwind_protect();
74-
7573
} // namespace detail
7674

7775
#ifdef HAS_UNWIND_PROTECT
@@ -82,11 +80,12 @@ static Rboolean& should_unwind_protect = get_should_unwind_protect();
8280
template <typename Fun, typename = typename std::enable_if<std::is_same<
8381
decltype(std::declval<Fun&&>()()), SEXP>::value>::type>
8482
SEXP unwind_protect(Fun&& code) {
85-
if (detail::should_unwind_protect == FALSE) {
83+
static auto should_unwind_protect = detail::get_should_unwind_protect();
84+
if (should_unwind_protect == FALSE) {
8685
return std::forward<Fun>(code)();
8786
}
8887

89-
detail::should_unwind_protect = FALSE;
88+
should_unwind_protect = FALSE;
9089

9190
static SEXP token = [] {
9291
SEXP res = R_MakeUnwindCont();
@@ -96,7 +95,7 @@ SEXP unwind_protect(Fun&& code) {
9695

9796
std::jmp_buf jmpbuf;
9897
if (setjmp(jmpbuf)) {
99-
detail::should_unwind_protect = TRUE;
98+
should_unwind_protect = TRUE;
10099
throw unwind_exception(token);
101100
}
102101

@@ -121,7 +120,7 @@ SEXP unwind_protect(Fun&& code) {
121120
// unset it here before returning the value ourselves.
122121
SETCAR(token, R_NilValue);
123122

124-
detail::should_unwind_protect = TRUE;
123+
should_unwind_protect = TRUE;
125124

126125
return res;
127126
}

0 commit comments

Comments
 (0)