How I disabled a single LLVM pass from Clang

I’m posting here how I solved my own problem in the hope that others may find it useful, since the Internet search results I found for this topic led me down wrong paths.

Using LLVM/Clang version 12 I wanted to disable a particular optimisation pass during -O3 optimisation, specifically the pass “AArch64 compress jump tables pass” defined in AArch64CompressJumpTables.cpp. After searching around I found this did not seem to have a builtin option in Clang to disable this one specific pass, and that it was automatically enabled as part of optimisation.

The solution I (eventually) found is that LLVM does have a flag to disable this pass, as can be seen in AArch64TargetMachine.cpp. Specifically, there is a hidden option aarch64-enable-compress-jump-tables which would disable the pass if we set it to 0, regardless of the -O3 setting. We can set this option from Clang using -mllvm -aarch64-enable-compress-jump-tables=0 for example. Hence clang -O3 -mllvm -aarch64-enable-compress-jump-tables=0 was the command line I needed to disable this pass. I ultimately noticed this by looking at a test case for the pass which used this flag to enable it.

In this case there was no need to write a plugin, interact with the pass manager, recompile anything, etc. The tool I needed was available out of the box, but Internet searches didn’t suggest this, and indeed seemed to suggest a more complex solution would always be necessary.


Thank you for helping future users!

Do you remember any places in the llvm documentation you looked at, that you would have expected to contain information like this? We can improve it if so.

Hmm, my first check was clang --help and since it was so verbose (1178 lines on my machine) I assumed that its list of flags was totally exhaustive. I tried searching that for a flag related to this specific optimisation and also tried searching that for keywords like ‘pass’. Having turned up nothing useful, I tried Internet searches like ‘Clang disable one optimisation pass’ which sent me to various forums that were not particularly helpful, and non drew attention to the key -mllvm flag that hid many more options that I didn’t appreciate until much later. Most results revolved around passes the do have Clang-exposed options, or else the advice was to write some plugin for the pass manager.

Perhaps drawing more attention to -mllvm might help? Is there a way to print all options it supports for example? Or at least to suggest in its documentation that it has many additional flags that can be searched.

Turns out there is but even then you need to know there is a help-hidden (I only know that because we use it a lot downstream). It is mentioned in --help but one wouldn’t know to look for it.

$ ./bin/clang /tmp/test.c -mllvm --help-hidden
USAGE: clang (LLVM option parsing) [options]
  --aarch64-enable-compress-jump-tables                                      - Use smallest entry possible for jump tables

I will try to improve the -mllvm help text for clang at least. We do have suggestions if you give it a bogus value, but you’d need to be close to what you wanted already:

$ ./bin/clang /tmp/test.c -mllvm --foo
clang (LLVM option parsing): Unknown command line argument '--foo'.  Try: 'clang (LLVM option parsing) --help'
clang (LLVM option parsing): Did you mean '--color'?

I’m not sure what Try: 'clang (LLVM option parsing) --help is supposed to mean. I guess it’s clang -mllvm --help but we should literally show that if that’s the case.

I’ll fix this too. Thanks for the feedback!

Or if you want to contribute yourself: Contributing to LLVM — LLVM 17.0.0git documentation

If you do want to do that, I’m happy to review for you.

Goodness, yes, that’s buried deep! In my case I seem to have to pass clang -mllvm --help-hidden test.c to even see the option. Neither clang --help-hidden nor clang -mllvm --help test.c show it, but I admit this is on version 12, not the current head. Furthermore the requirement to pass a C file is not something I would expect. I can see why it’s there from a technical perspective, it’s not something a user is likely to try unprompted and it results in a link error.

Ah yes, I also saw that once and didn’t know how to interpret it, that makes sense.

I might end up trying to contribute something else later, so I suppose it’s worth a go for me to do it. Is the documentation all in the ‘clang’ repository?

Basically yes but in this case some of it will be in llvm/. Best way to find things is to search in the monorepo for the message or the parts of the message that are likely static.

Side note: the new Github code search feature is a quick way to do this e.g. Sign in to GitHub · GitHub . Though it seems to require you to login to Github to do that.

In this case Try: found it in llvm-project/llvm/lib/Support/CommandLine.cpp at 1f1385d93204b334d1d8ca13792916ca726e17eb · llvm/llvm-project · GitHub. I guess that by default the argv there prints as some descriptive name not the option itself.

Other options text will be found in a TableGen (.td) file and documentation pages for the website are usually .rst files.