# [IR][Pass][Instrument] Pass Instrument Framework

https://github.com/apache/tvm/pull/7952

Proposal 
=======


Currently in TVM, there are trace mechanisms and passes time profiling.

* ### Trace
```cpp
/*!
 * \brief PassContextNode contains the information that a pass can rely on,
 * such as analysis results.
 * \sa PassContext
 */
class PassContextNode : public Object {
 public:
  // Skipped

  /*! \brief Trace function to be invoked before and after each pass. */
  TraceFunc trace_func;

  // Skipped
```

* ### Pass Time Profiling
https://github.com/apache/tvm/pull/7500

## They have similar semantics that want to profile/trace passes.


## This PR tries to generalize and integrate the concepts:
   ### 1. Trace is rename to PassInstrumentors with more functionalities:
   *   Explicitly split RunBeforePass and RunAfterPass into different functions 
instead of checking in trace call back funcion.
         ```
        def trace(ir_module, pass_info, is_before):
            if is_before:
                # Before Pass Run
            else:
                # After Pass Run
               
       # ==>

       pi = tvm.instrument.PassInstrument()
       
       @pi.register_run_before_pass
       def run_before_pass(ir_module, pass_info):
             # Before Pass Run

       @pi.regiser_run_after_pass
       def run_after_pass(ir_module, pass_info):
             # After Pass Run
            
       @pi.register_set_up
       def set_up():
             # Instrumentation environment set up

       @pi.register_tear_down
       def tear_down():
             # Instrumentation environment clean up
        ```
   *  PassInstrumentor collects a set of PassInstrument instead of single call 
back
       ```
      with tvm.transform.PassContext(Trace=_trace):
           # Call _trace in build flow

      # ==>  

      pi1 = tvm.instrument.PassInstrument()
      pi2 = tmv.instrument.PassInstrument()
      with tvm.transofm.PassContext(
            pass_instrumentor=tvm.instrument.PassInstrumentor([pi1, pi2]):
          # Call pi1 and pi2's callbacks in build flow
      ```
    
  ### 2. Provide a PassesTimeInstrument that leverages previous passes time 
profiling c++ code.
```cpp
 TVM_REGISTER_GLOBAL("instrument.MakePassesTimeInstrument").set_body_typed([]() 
{
  auto pi = PassInstrument("PassesTimeInstrument");
  // No set up function for this time instrumentation.
  pi->RegisterTearDownCallback([]() { 
PassProfileThreadLocalStore::Get()->root.children.clear(); });
  pi->RegisterRunBeforePassCallback([](const IRModule&, const 
transform::PassInfo& pass_info) {
    PassProfile::EnterPass(pass_info->name);
    return true;
  });

  pi->RegisterRunAfterPassCallback(
      [](const IRModule&, const transform::PassInfo&) { 
PassProfile::ExitPass(); });

  return pi;
});

```
  ### 3. Inspired by LLVM and MLIR, it might be good to let run_before_pass() 
determines whether to run a pass with some instrumentation logics. (Return true 
to run pass; return false to skip pass)

```cpp
/*!
 * \file tvm/ir/instrument.h
 *
 * This file implements a pass instrument infrastructure, inspired from LLVM 
and MLIR.
 * It inserts instrumentation points between passes run.
 *
 * Within a pass context (tvm::transfom::PassContext), the instrumentation call 
sequence will like:
 *
 *   Instrument SetUp
 *
 *     if (Instrument Before Pass)
 *       Pass Run
 *       Instrument After Pass
 *
 *     if (Instrument Before Pass)
 *       Pass Run
 *       Instrument After Pass
 *
 *   Instrument TearDown
 *
 *
 * Instrument point before pass can determine particular pass is disable or not 
depends on the
 * callback registered.
 */
```


## Some Question Received
Thanks to **[tkonolige]** and **[tqchen]**

### Q.

**[tkonolige]**
> In order to avoid duplicating code it might be worth unifying this with the 
> runtime profiling framework. I have a branch (which I haven't submitted yet) 
> that allows users to extend which kinds of information are collected. 

**[tqchen]**
> I agree it is important to have pass instrumentations, would be good to know 
> how can it interact with Trace, since some of the callbacks might be similar 
> and we need to unify the interface. On the design side, I think the runtime 
> profiling and pass instrumentation might be different enough that might worth 
> two separate solutions(perhaps a bit of reuse of timer if needed) As the 
> former have more complexity wrt to GPU timer etc, while the later allows more 
> statistics to be collected

### A.
I would like to separate runtime profiling and pass instrumentation, too. This 
PR only focuses on pass profiling mechanisms like the passes time profiling, 
wants to make it easier to add more passes profiling implementations. 

You might notice that this PR introduces a new namespace tvm.intrument. It 
intends to cover all instrument related (not limited to pass, but this PR  only 
shows pass instrument), instead of mixing instrumentation/profiling code with 
transformation codes in tvm.transform.
RuntimeProfiling could be add to this namespace, eg: 
tvm.instrument.Runtime.Profiling.


# Please let me know how you think about this proposal :slight_smile:





---
[Visit 
Topic](https://discuss.tvm.apache.org/t/pass-instrument-framework-proposal/9874/1)
 to respond.

You are receiving this because you enabled mailing list mode.

To unsubscribe from these emails, [click 
here](https://discuss.tvm.apache.org/email/unsubscribe/8549949a8b1c80259ef1fa968dc48814a7fd6fb8b827c6e206a143aac3856a3a).

Reply via email to