FPGA開発日記

カテゴリ別記事インデックス https://msyksphinz.github.io/github_pages , English Version https://fpgadevdiary.hatenadiary.com/

MLIRの勉強 (7. rewriterの勉強)

MLIRについて勉強している。

いくつかの最適化について実装してみたくて、例えばA-Aを自動的に0としてくれるみたいなのは簡単に作れそうなのだけれども、MLIRのrewriterというのを使うらしい。

   /// This method attempts to match a pattern and rewrite it. The rewriter
   /// argument is the orchestrator of the sequence of rewrites. The pattern is
   /// expected to interact with it to perform any changes to the IR from here.
   mlir::LogicalResult
   matchAndRewrite(TransposeOp op,
                   mlir::PatternRewriter &rewriter) const override {
     // Look through the input of the current transpose.
     mlir::Value transposeInput = op.getOperand();
     TransposeOp transposeInputOp = transposeInput.getDefiningOp<TransposeOp>();

     // Input defined by another transpose? If not, no match.
     if (!transposeInputOp)
       return failure();

     // Otherwise, we have a redundant transpose. Use the rewriter.
     rewriter.replaceOp(op, {transposeInputOp.getOperand()});
     return success();
   }
 };

このrewriterを使えば何かできると思うのだが、「削除」ではなく「追加」するとすればどうやればいいんだろう。

   mlir::LogicalResult
   matchAndRewrite(SubOp op,
                   mlir::PatternRewriter &rewriter) const override {
     // Look through the input of the current transpose.
     mlir::Value op0 = op.getOperand(0);
     mlir::Value op1 = op.getOperand(1);

     mlir::Type elementType = rewriter.getI64Type();

     mlir::Value zero = rewriter.create<ConstantOp>(op.getLoc(), elementType, /*value=*/0);

     rewriter.replaceOp(op, zero);
     return success();
   }

あれ、何にも変わらなかった。

$ ./bin/mysv --emit=mlir ../mlir/examples/mysv/test/assign_ops2.sv
module {
  %0 = "mysv.constant"() {value = 3 : si64} : () -> i64
  %1 = "mysv.constant"() {value = 4 : si64} : () -> i64
  %2 = "mysv.sub"(%0, %0) : (i64, i64) -> i64
  %3 = "mysv.add"(%2, %1) : (i64, i64) -> i64
  %4 = "mysv.mul"(%0, %1) : (i64, i64) -> i64
}