I want to take out the address of memref by pass.inputvalue
is generated by memref.alloc
.I want to take out its address. Then pass in the other op.
matchAndRewrite(MvinOp mvinOp, OpAdaptor adaptor,
ConversionPatternRewriter &rewriter) const override {
mlir::Value inputValue = mvinOp.getInput();
}
I’m not sure what you mean by “take out its address”, when you write mlir::Value inputValue = mvinOp.getInput();
the inputValue
is a “handle” to the memref value itself. This is what to use if you want to pass the memref to another operation as operand.
For example.Lower the following code to the llvm dialect.
func.func @main() {
%c0 = arith.constant 0 : index
%c1 = arith.constant 1 : index
%mem0 = memref.alloc() : memref<2x3xf32>
%mem1 = memref.cast %mem0 : memref<2x3xf32> to memref<?x?xf32>
%dim0 = memref.dim %mem0, %c0 : memref<2x3xf32>
%dim1 = memref.dim %mem0, %c1 : memref<2x3xf32>
%dim2 = memref.dim %mem1, %c0 : memref<?x?xf32>
%dim3 = memref.dim %mem1, %c1 : memref<?x?xf32>
vector.print %dim0 : index
vector.print %dim1 : index
vector.print %dim2 : index
vector.print %dim3 : index
memref.dealloc %mem0 : memref<2x3xf32>
func.return
}
Here are the results of lower.
module attributes {llvm.data_layout = ""} {
llvm.func @printNewline()
llvm.func @printU64(i64)
llvm.func @free(!llvm.ptr<i8>)
llvm.func @malloc(i64) -> !llvm.ptr<i8>
llvm.func @main() {
%0 = llvm.mlir.constant(2 : index) : i64
%1 = llvm.mlir.constant(3 : index) : i64
%2 = llvm.mlir.null : !llvm.ptr<f32>
%3 = llvm.getelementptr %2[6] : (!llvm.ptr<f32>) -> !llvm.ptr<f32>
%4 = llvm.ptrtoint %3 : !llvm.ptr<f32> to i64
%5 = llvm.call @malloc(%4) : (i64) -> !llvm.ptr<i8>
llvm.call @printU64(%0) : (i64) -> ()
llvm.call @printNewline() : () -> ()
llvm.call @printU64(%1) : (i64) -> ()
llvm.call @printNewline() : () -> ()
llvm.call @printU64(%0) : (i64) -> ()
llvm.call @printNewline() : () -> ()
llvm.call @printU64(%1) : (i64) -> ()
llvm.call @printNewline() : () -> ()
llvm.call @free(%5) : (!llvm.ptr<i8>) -> ()
llvm.return
}
}
You can see that there are two lines of code.
%3 = llvm.getelementptr %2[6] : (!llvm.ptr<f32>) -> !llvm.ptr<f32>
%4 = llvm.ptrtoint %3 : !llvm.ptr<f32> to i64
Here I want to get %4
, more specifically, I want the address of the memory int type
.
This is a property of the lowering to the LLVM dialect. I would encourage to describe with more detail the entire flow of what you’re trying to accomplish (maybe with an example) so that we can provide with the best answer here.
I’m sorry, my language skills are not very good.My op needs to input the memory allocated by memref
, then I need to write pass, then get the address of type int
allocated memory in the pass, and then I can rewrite the op.
I suspect we’re getting into a “5 why’s” kind of pattern, where I’ll be asking “why do you needs to input the memory allocated by memref
and get the address of type int allocated memory in the pass
?” and again on the next answer until we get the full story.
Overall if you’re working with memref, it is quite unlikely that you need to extra the address (until you lower the op to LLVM). At this level the memref value should be all you need.
(there are some very advanced use-case where it isn’t totally true, but I’d rather get the full story of what you’re trying to accomplish before getting there).
It’s a long story. I actually extended it a little bit on the risc-v instruction.The original version uses the c language array
to alloc memory. The instructions are then written using inline assembly. One argument that the assembly instruction requires is the address of the array. So here I want to get the address of memref in pass and then convert to intrinsics
.Then convert intrinsics
to the assembly instruction
.
Isn’t memref.extract_aligned_pointer_as_index operation is what you are looking for?
1 Like
I did the relevant tests and successfully took out the memref address. The program runs fine.Thanks!