|Anonymous | Login | Signup for a new account||2018-05-25 16:56 CEST|
|Main | My View | View Issues | Change Log | Roadmap|
|View Issue Details|
|ID||Project||Category||View Status||Date Submitted||Last Update|
|0007718||OCaml||typing||public||2018-02-01 02:02||2018-02-01 09:29|
|Priority||normal||Severity||minor||Reproducibility||have not tried|
|Target Version||Fixed in Version|
|Summary||0007718: Bad interraction between let-rec and no-naked-pointers|
|Description||There are many kind of expressions that can't be preallocated, but are considered as having a 'Static' size by Typecore.classify_expression. For instance 'new' or 'while'.|
Those cases are compiled by two let bindings, one bound to 0, the second to the real value. This should be correct only when those 0 bindings can't be reached. I didn't find any example of any value classified as static size, that can't be preallocated, but that can contain a pointer to another value from the let-rec bound variables. (without using the 0007706 bug). I might have stopped looking too early.
Yet that pointer can be reached. The GC can traverse it. For instance
class a =
let () = Gc.full_major () in
let rec b =
let x = (b,b) in
let v = new a in
let y = (x, x) in
The critical part being compiled to:
(x/1009 (alloc block-hdr(2048) b/1008 b/1008)
(let fun/1060 (load_mut val (load_mut val "camlNew"))
(app (load_mut val fun/1060) 1a fun/1060 val))
y/1011 (alloc block-hdr(2048) x/1009 x/1009))
The block x/1009 contains values '0' which can't be scanned in no-naked-pointer
mode and can lead to segfaults.
In that specific case, the problem is hidden by another, but assuming that 0007706
is fixed, this one remains. I just needed to let bind the new to ensure that x is
alive across the call.
One could argue that this 0 should be replaced by something that the gc can scan,
like 1. But I would argue that this should rather be rejected.
If 'new' was considered as non-static sized (which it's clearly isn't since the
value is built by a function application) this would be rejected because this
expression depends on b which is invalid at that point. And I consider that to
be the true problem here.
Also I suggest renaming 'Static' to 'Can_be_preallocated'.
|Tags||No tags attached.|
I'm currently writing a new shared version of the compilation of let-rec and noticed that while trying to justify its correctness. I'm trying to avoid having to preallocate functions and this kind of edge cases add some serious complexity while probably never being produced.
I would even argue that rejecting this kind of code is a good idea in general, without considering whether it is possible to compile them or not. This could only reject a programs in presence of dead code.
|2018-02-01 02:02||chambart||New Issue|
|2018-02-01 02:09||chambart||Note Added: 0018863|
|Copyright © 2000 - 2011 MantisBT Group|