[Rd] Forcing a PROTECT Bug to Occur

Tomas Kalibera tom@@@k@||ber@ @end|ng |rom gm@||@com
Sat Apr 29 20:04:13 CEST 2023


On 4/29/23 19:26, Michael Milton wrote:
> I'm trying to learn about R's PROTECT system. To that end I've tried to
> create an example of C code that doesn't protect anything. I was hoping it
> would either segfault from trying to access deallocated memory, or maybe
> print out nonsense results because the unprotected memory got overwritten,
> but I can't make either happen.
>
> Here's my current code (all in R, using the inline package for simplicity):
>
>> gctorture(TRUE)
>> z = inline::cfunction(body="
>      SEXP vec_1 = Rf_ScalarInteger(99);
>      SEXP vec_2 = Rf_allocVector(VECSXP, 10);
>      SET_VECTOR_ELT(vec_2, 1, vec_1);
>      Rf_PrintValue(vec_2);
> ")
>
> My thinking was that, with torture mode enabled, the allocation of vec_2
> should ensure that vec_1 is collected, and then trying to put it into vec_2
> and then print it would then fail. But it consistently prints 99 in the
> list's second element.
>
> Why does this code not have issues? Alternatively, is there a simpler
> example of C code that demonstrates missing PROTECT calls?

It is not guaranteed that a PROTECT error will always lead to memory 
corruption or a crash in all executions of a program, not even with 
gctorture.

To increase the chances, you can instruct gctorture to run the gc more 
often (but the execution would be slower). You can build R with strict 
write barrier checking (see e.g. Writing R Extensions, look for 
gctorture) to make it more likely errors will be detected. There is 
always a tradeoff between this probability and slowdown of the 
execution. In theory we could invalidate all unreachable objects at 
every allocation, but that would be so slow that we could not test any 
programs in practice.

Then, not every piece of memory can be used by any allocation, due to 
how the memory allocator and gc works. If you need to provoke an error 
e.g. for educational purposes, perhaps chances would be higher if you 
allocate an object of the same type and size as the one not protected in 
error.

You can also play with R sources - e.g. introduce a PROTECT error into 
some key part of the R interpreter, it should not be too hard to trigger 
that via make check-devel.

Best
Tomas

>
> 	[[alternative HTML version deleted]]
>
> ______________________________________________
> R-devel using r-project.org mailing list
> https://stat.ethz.ch/mailman/listinfo/r-devel



More information about the R-devel mailing list