Problems with "can't create Attribute"

Hi, all,
I build my custom dialect like

flow.func @main() {
    // %0 = flow.constant dense<[[1.000000e+00, 2.000000e+00, 3.000000e+00], [4.000000e+00, 5.000000e+00, 6.000000e+00]]> : tensor<2x3xf64>
    // %1 = flow.constant dense<[[1.000000e+00, 2.000000e+00, 3.000000e+00], [4.000000e+00, 5.000000e+00, 6.000000e+00]]> : tensor<2x3xf64>
    // %2 = flow.add %1, %0: tensor<2x3xf64>
    // %3 = flow.mul %1, %0: tensor<2x3xf64>
    // %4 = flow.sub %3, %2: tensor<2x3xf64>
    // %5 = flow.div %4, %3: tensor<2x3xf64>
    // flow.print %5: tensor<2x3xf64>
    %0 = flow.constant dense<[1.0, 2.0, 3.0, 4.0, 9.0, 32.0]> : tensor<6xf64>
    %2 = flow.sum %0: tensor<6xf64> to f64
    %3 = flow.dot %0, %0: tensor<6xf64>, tensor<6xf64> to f64
    // %4 = math.atan %3: f64
    flow.print %3: f64
    flow.return
}

I compiled it successfully.
but when i use %4 = math.atan %3: f64, the error with

LLVM ERROR: can't create Attribute 'mlir::arith::FastMathFlagsAttr' because storage uniquer isn't initialized: the dialect was likely not loaded, or the attribute wasn't added with addAttributes<...>() in the Dialect::initialize() method.
Aborted (core dumped)

What does your main function look like? Maybe the Math dialect is not loaded correctly? I get a different error when I don’t load the Math dialect but when I do, it gets parsed without problem.

It appears that the arith dialect is not loaded, and that math should be declaring a dependency on it because it uses attributes from it. Try loading arith when you create the context.

⚙ D147999 [mlir] make Math dialect depend on Arith dialect should fix it.

void FlowToAffineLowingPass::runOnOperation() {
  ConversionTarget target(getContext());
  target.addLegalDialect<AffineDialect, BuiltinDialect, math::MathDialect, arith::ArithDialect, func::FuncDialect,
                         memref::MemRefDialect, vector::VectorDialect, scf::SCFDialect>();
  target.addIllegalDialect<flow::FlowDialect>();
  target.addDynamicallyLegalOp<flow::PrintOp>([](flow::PrintOp op) {
    return llvm::none_of(op->getOperandTypes(),
                         [](Type type) { return type.isa<TensorType>(); });
  });

  RewritePatternSet patterns(&getContext());
  patterns.add<FuncOpLowering, ReturnOpLowering, ConstantOpLowering,
               PrintOpLowering,
               AddOpLowering, SubOpLowering, MulOpLowering, DivOpLowering,
               SumOpLowering, DotOpLowering>(&getContext());
  if (failed(applyPartialConversion(getOperation(), target, std::move(patterns))))
    signalPassFailure();
}

Looks I loaded arith correctly.

  mlir::registerAllPasses();
  mlir::DialectRegistry registry;
  mlir::registerAllDialects(registry);
  registry.insert<mlir::flow::FlowDialect>();
  mlir::MLIRContext context(registry);

  mlir::OwningOpRef<mlir::ModuleOp> module;
  if (int error = loadAndProcessMLIR(context, module))
    return error;

Nope. Pattern rewriter configuration doesn’t load dialects, and neither does registration, see FAQ - MLIR. That being said, it should be loaded when math is loaded by the parser, but math is missing a dependency declaration. That’s what my patch fixes.

Thanks,I got it.

Thanks.
But how can I fix this problem in my custom project. Because when I look math.td in latest main repo, but I do not find your patch in main repo. So if I want to fix this porblem, should I add

let dependentDialects = [
    "::mlir::arith::ArithDialect"
  ];

this contect to my local mlir/include/mlir/Dialect/Math/IR/MathBase.td and rebuild llvm project ?

You can apply the patch directly to your copy of the source tree or as git cherry-pick after it lands (I’d recommend creating a branch so you see what changes you added compared to the mainline project).

finally, I use

context.loadAllAvailableDialects();

solved my problems. I need to read mlir-opt source file firstly.