[RFC] Dialect::registerDependentDialects

Ideally, I would think that an MLIR built with NDEBUG enables all the checks that makes anyone developing an MLIR based project more productive: we should catch as early as possible and with the best diagnostic possible any mis-use of APIs.
I would consider MLIR_EXPENSIVE_CHECKS if we have checks that makes it prohibitive to runs with assert enable to the point where it is counterproductive (people will disable assert instead because the project becomes too slow).
I don’t know what the cost of this feature would be, but I could also see this as an option on the pass manager (so that it is more flexible than just in-or-out the things available in an assert build).

This sort of thing is why NDEBUG is basically impossible to use for anything that depends on LLVM though. It may make MLIR developers more productive, but it makes anyone else trying to use NDEBUG less productive because now they’re doing tons of extra work. Having those sorts of things scoped per-project is much nicer IMO.

1 Like

I don’t quite get your point though: you can build LLVM/MLIR with or without assert and use them in your project which will use assert or not independently: renaming our assert macro should change much here, at least it seems to me to be entirely orthogonal to the MLIR_EXPENSIVE_CHECKS question.

Not really, but what’s important here is the nature of behavior. A fatal error message or assert is useful but silently unloading dialects and the messages they result in could be confusing. It also doesn’t address the question of why a dialect that was explicitly loaded by a user (before a pipeline was called) was unloaded – it appears undesirable whether in debug mode or release mode.

I believe it is still a bug from the Pass pipeline API contract to not provide it in the getDependentDialect() list.

That’s right. It would be a bug but consider the scenario where there is no bug (all passes have their dependent dialects correctly specified): unloading dialects would break a tool doing an IR mutation outside of any pass after the pass pipeline has been run – because the expected dialects don’t remain loaded at the end. (Consider a translation scenario from another IR to MLIR where not all mutations may happen in passes.)

“unloading” is kind of a shorthand. When we discussed how this might be implemented, it would probably be some sort of bookkeeping instead. Regardless, I would expect that at the end of a pipeline the dialects loaded in the context should be restored such that whether or not this mode is enabled does not alter things outside of pass pipelines

2 Likes

Right it would be an unload/reload kind of thing: the system would be in the same state before and after the pass pipeline runs.

Linking LLVM/MLIR code built with NDEBUG and my code linked without would give ODR violations, no?

It should not, at least it’s not that simple: LLVM has a special macros for controlling “ABI breaking checks” related to assertion mode independently of “NDEBUG”.
See: llvm-project/HandleLLVMOptions.cmake at main · llvm/llvm-project · GitHub

If you can link/execute your application, you should be good to go!

We’re rather off on a tangent, but in IREE we’ve had all kinds of issues with LLVM_ENABLE_ASSERTIONS: Combination of `-DCMAKE_BUILD_TYPE=Release -DLLVM_ENABLE_ASSERTIONS=ON` is horribly broken · Issue #5750 · google/iree · GitHub