Ban Prim_poly from Lambda#2189
Ban Prim_poly from Lambda#2189mshinwell wants to merge 7 commits intooxcaml:5.1.1minus-5-microbranchfrom
Conversation
|
@goldfirere is looking at this one. |
|
I think this fixes the bug (thanks for the test @ncik-roberts), and looks reasonable. I made a number of (what I believe are) improvements, but my commits need further review. |
|
I think this probably isn't the best approach. The primitive type is intended to describe the information from an In other words, leave the |
|
Actually, thinking about it more, I don't think this statement is true for C calls:
which means there is no problem with the existing So, I think you just need a one line fix in |
|
Superceded by #2190 |
In #2180 there were really two fixes:
Call_kindin Flambda 2 to deal with the accidental omission of the region variable for C calls during a recent improvement/refactoring PR (Better region handling for functions #1871).Lambda.primitive_may_allocateto correctly handle the case whenprim_allocisfalsebut in fact the external function locally allocates. This appears to have been a pre-existing bug. (It is permitted to write such code iff you are certain the compiler used will always be configured with stack allocation.)Unfortunately the second change has revealed another problem. Some primitives, for example one declared like this:
end up appearing in Lambda as
Prim_poly(the comment inprimitive.mliis kind of misleading here). However this isn't ok from the point of view ofLambda.primitive_may_allocateand in particular its new helper functionLambda.alloc_mode_of_primitive_description(which is also used by Flambda 2). For example, the above primitive might get eta-expanded by the code inTranslprim, in conjunction with a judgement that effectively turnsPrim_poly(plus some extra information, thepoly_mode) intoAlloc_heap. This is then used to avoid inserting a region, correctly, but is not propagated further (there is nowhere to put it on theLambdaterms). We thereby end up in a situation where the Lambda code saysPrim_poly, soalloc_mode_of_primitive_descriptionsays "might allocate locally" -- but theTranslprimcode had not inserted a region. This then causes a fatal error in Flambda 2, because if a external call might allocate locally, its applications will contain region variables. These will be unbound if the frontend failed to insert the appropriate regions (or marked the enclosing function as allowing local allocations to escape, in which case the implicitmy_regionfunction parameter would be used).The idea of this PR is to ban
Prim_polyfrom appearing in Lambda terms at all. It does this by making the argument of thePccallconstructorprivate, which necessitates only minor changes, and insisting that all constructions of it are done by supplying the return mode. This then rewritesPrim_polyinto eitherPrim_globalorPrim_localas appropriate, avoiding the above problem. It seems better than an alternative solution I considered, namely causing regions to be inserted for allPrim_polyprimitive calls.