
Max Bolingbroke wrote:
If you don't need a dependency and it can be ignored anyway, why would you want to specify it in the first place? I just can't quite imagine a situation in which I would use this.
I think it makes sense because many of the inter-pass dependencies we have in the GHC pipeline today are actually somewhat lenient. For example, something quite sensible will happen if we do CSE before full laziness, it will simply lead to less efficient code. In contrast, it's imperative that we perform strictness analysis before applying worker-wrapper based on the annotations it adds.
I see. I suspect I'd prefer if GHC asked me to manually resolve such conflicts rather than silently generating suboptimal code but then again, perhaps not. In any case, my comments mostly apply to phase control for inlining and rule matching; other passes probably have different requirements which I haven't thought about at all.
Yeah, I'd prefer the class/instance model. An example: suppose you have two independent libraries which implement two optimisations and you want one of them to run before another. I think we really need this if we want to compose optimisations.
This is an interesting observation. So, you imagine that the >user program itself< might import the compiler plugins and add a constraint between the phases they export. I'm not sure how many users would really want to do this, but I can see it being useful.
What I had in mind is a library/plugin which uses other libraries/plugins. For instance, let's say we have two libraries which both implement rule-based fusion, one for some high-level stuff and one for something low level. Now, a third library which uses the first two might want to specify that high-level fusion should be done before low-level fusion. Or consider something like loop optimisations, where you might have separate plugins which implement unrolling, PRE and so on and one plugin which aggregates all these to provide a complete loop optimiser. It's all about compositionality, really. Roman