Ecosyste.ms: Awesome

An open API service indexing awesome lists of open source software.

Awesome Lists | Featured Topics | Projects

https://github.com/davisvaughan/testcpp11unwind

What the Package Does (One Line, Title Case)
https://github.com/davisvaughan/testcpp11unwind

Last synced: 7 days ago
JSON representation

What the Package Does (One Line, Title Case)

Awesome Lists containing this project

README

        

---
output: github_document
---

```{r, include = FALSE}
knitr::opts_chunk$set(
collapse = TRUE,
comment = "#>",
fig.path = "man/figures/README-",
out.width = "100%"
)
```

# testcpp11unwind

```{r, error = TRUE}
# Destructor is run
testcpp11unwind:::call_A()

# Destructor is NOT run
testcpp11unwind:::call_B()
```

Note that `cpp_A()` and `cpp_B()` on their own are seemingly innocuous code that a developer is likely to write without thinking twice about it.

The destructor of `a` doesn't run in the `cpp_B()` case because:

- `call_B()` sets up a try/catch through the entry macros
- `fn()` calls `unwind_protect()` and sets `should_unwind_protect = FALSE`
- `R_UnwindProtect()` is used to call `call_A()`, and a `setjmp()` is used
to be able to recover from `longjmp()`s
- `call_A()` sets up a try/catch through the entry macros
- `cpp_A()` is called
- `a` is created
- `stop()` calls `unwind_protect()`, but `should_unwind_protect = FALSE` so
it does NOT use `R_UnwindProtect()` or `setjmp()`
- `stop()` ends up calling `Rf_error()`, causing a `longjmp()`
- Because `should_unwind_protect = FALSE`, the `longjmp()` is not caught in
`stop()`. Instead we jump alllll the way back to where `fn()` called
`unwind_protect()` and `R_UnwindProtect()`. This skips over the `cpp_A()`
frame where `a` should have been destructed on the way out. VERY BAD!