Pass Scheduling Information without using opt

Hello everybody,

is it somehow possible to get information about what passes were run in what order or timing analysis of passes *without* using opt?
I am implementing a ModulePass that at some point creates a FunctionPassManager which runs several passes, but I cannot figure a way to output the same information as when running a command line tool as described in "Writing an LLVM Pass".

Regards,
Ralf

Hi Ralf,

I believe all you need to do is call llvm::llvm_shutdown().

- Daniel

Hey Daniel,

thanks for the response.

I believe all you need to do is call llvm::llvm_shutdown().
  

I am not sure that this is what I need. When and how should I call llvm_shutdown()?
After the FunctionPassManager is done, the calling ModulePass still performs quite a few actions on the transformed code and also calls the FunctionPassManager on different functions. However, I need to display statistics about the transformation of each function separately.
If I call llvm_shutdown() after the FunctionPassManager is finished, I do not get any output. Instead, the bitcode seems to get corrupted (at least the verifier reports a lot of "Intrinsic has wrong parameter attributes" warnings, the code still runs fine).

Cheers,
Ralf

Hey Daniel,

thanks for the response.

I believe all you need to do is call llvm::llvm_shutdown().

I am not sure that this is what I need. When and how should I call
llvm_shutdown()?

At the end of the program, this just arranges for LLVM's "managed
statics" to be shutdown, which will triggering the printing of pass
information.

After the FunctionPassManager is done, the calling ModulePass still
performs quite a few actions on the transformed code and also calls the
FunctionPassManager on different functions. However, I need to display
statistics about the transformation of each function separately.

Ah, in this case llvm_shutdown isn't what you are looking for. I've
never looked at the Statistic implementation so I can't be any help
here, but if you poke around starting with "llvm/ADT/Statistic.h" you
may find a way to do what you want.

- Daniel

Daniel Dunbar wrote:

Ah, in this case llvm_shutdown isn't what you are looking for. I've
never looked at the Statistic implementation so I can't be any help
here, but if you poke around starting with "llvm/ADT/Statistic.h" you
may find a way to do what you want.

I looked into that already, but Statistic.h only gives me the
possibility to implement tracking and printing of my own statistics.
What I want should be located somewhere in the PassManagers, but I do
not find anything helpful. DbgInfoPass only prints out the cfg, same for
CFGPrinterPass (which I can do better by using viewCFG() anyways).
I also found PMDataManager::dumpPassInfo(), but could not get any
information out of it - however, I am also not sure how to use it
correctly and I guess it will probably also not provide statistics about
the PassManager run as a whole.

Here is some example code that describes what I am doing:

MyPass : ModulePass {

bool runOnModule(mod) {

for some Functions f in mod {
(do some stuff)

ExistingModuleProvider mp(mod);
FunctionPassManager* fpm =
new FunctionPassManager(&mp);

fpm->add(createLowerSwitchesPass());
fpm->add(createBreakCriticalEdgesPass());
fpm->add(createLoopSimplifyPass());

fpm2->run(*f);

mp.releaseModule();

(do more stuff)
}

}

}

Now what I want to have is some runtime-output of the pass manager that
tells me what passes were run in what order, give me timing information
if possible etc.

I hope my explanation is better this time :).

Cheers,
Ralf

Here is some example code that describes what I am doing:

MyPass : ModulePass {

bool runOnModule(mod) {

for some Functions f in mod {
(do some stuff)

ExistingModuleProvider mp(mod);
FunctionPassManager* fpm =
new FunctionPassManager(&mp);

I think creating a new Function Pass Manager inside a module pass is
not ideal, however...

fpm->add(createLowerSwitchesPass());
fpm->add(createBreakCriticalEdgesPass());
fpm->add(createLoopSimplifyPass());

fpm2->run(*f);

mp.releaseModule();

(do more stuff)
}

}

}

Now what I want to have is some runtime-output of the pass manager that
tells me what passes were run in what order, give me timing information
if possible etc.

You can set global PassDebugging enum. The pass manager will print
useful info while it is running. See initial part of
VMCore/PassManager.cpp for more information on PassDebugging enum.

Hey Devang,

thanks for your answer! :slight_smile:

Devang Patel schrieb:

I think creating a new Function Pass Manager inside a module pass is
not ideal, however...
  

Currently, I don't see any other way to do it - I need to generate new functions and thus need to have access to the whole module. Plus, the pass involves some overhead that only has to be computed once per module instead of once per function.
However, the module pass itself is not really used: the class is instantiated directly using a wrapper...
If you have any general suggestions on how you would try to handle this, please tell me. :slight_smile:

You can set global PassDebugging enum. The pass manager will print
useful info while it is running. See initial part of
VMCore/PassManager.cpp for more information on PassDebugging enum.

I tried that, but I don't understand how this is working and how/what I should set :(.

Regards,
Ralf