1 // Test that bind_c derived type results are not moved to a hidden argument
2 // by the abstract-result pass. They will be dealt with according to the C
3 // struct returning ABI for the target in the target-rewrite pass.
4 // RUN: fir-opt %s --abstract-result | FileCheck %s
6 !t = !fir.type<t{i:f32, j: i32, k: f32}>
7 !cptr = !fir.type<_QM__fortran_builtinsT__builtin_c_ptr{__address:i64}>
9 func.func private @foo() -> !t attributes {fir.proc_attrs = #fir.proc_attrs<bind_c>}
11 func.func @test_call(%x: !fir.ref<!t>) {
12 %0 = fir.call @foo() proc_attrs<bind_c> : () -> !t
13 fir.save_result %0 to %x : !t, !fir.ref<!t>
17 func.func @test_addr_of() -> (() -> !t) {
18 %0 = fir.address_of(@foo) : () -> !t
22 func.func @test_dispatch(%x: !fir.ref<!t>, %y : !fir.class<!fir.type<somet>>) {
23 %0 = fir.dispatch "bar"(%y : !fir.class<!fir.type<somet>>) (%y : !fir.class<!fir.type<somet>>) -> !t proc_attrs<bind_c> {pass_arg_pos = 0 : i32}
24 fir.save_result %0 to %x : !t, !fir.ref<!t>
29 func.func private @return_cptr() -> !cptr attributes {fir.proc_attrs = #fir.proc_attrs<bind_c>}
30 func.func @test_return_cptr(%x: !fir.ref<!cptr>) {
31 %0 = fir.call @return_cptr() proc_attrs<bind_c> : () -> !cptr
32 fir.save_result %0 to %x : !cptr, !fir.ref<!cptr>
37 // CHECK-LABEL: func.func @test_call(
38 // CHECK-SAME: %[[VAL_0:.*]]: !fir.ref<!fir.type<t{i:f32,j:i32,k:f32}>>) {
39 // CHECK: %[[VAL_1:.*]] = fir.call @foo() proc_attrs<bind_c> : () -> !fir.type<t{i:f32,j:i32,k:f32}>
40 // CHECK: fir.store %[[VAL_1]] to %[[VAL_0]] : !fir.ref<!fir.type<t{i:f32,j:i32,k:f32}>>
43 // CHECK-LABEL: func.func @test_addr_of() -> (() -> !fir.type<t{i:f32,j:i32,k:f32}>) {
44 // CHECK: %[[VAL_0:.*]] = fir.address_of(@foo) : () -> !fir.type<t{i:f32,j:i32,k:f32}>
45 // CHECK: return %[[VAL_0]] : () -> !fir.type<t{i:f32,j:i32,k:f32}>
47 // CHECK-LABEL: func.func @test_dispatch(
48 // CHECK-SAME: %[[VAL_0:.*]]: !fir.ref<!fir.type<t{i:f32,j:i32,k:f32}>>,
49 // CHECK-SAME: %[[VAL_1:.*]]: !fir.class<!fir.type<somet>>) {
50 // CHECK: %[[VAL_2:.*]] = fir.dispatch "bar"(%[[VAL_1]] : !fir.class<!fir.type<somet>>) (%[[VAL_1]] : !fir.class<!fir.type<somet>>) -> !fir.type<t{i:f32,j:i32,k:f32}> proc_attrs <bind_c> {pass_arg_pos = 0 : i32}
51 // CHECK: fir.store %[[VAL_2]] to %[[VAL_0]] : !fir.ref<!fir.type<t{i:f32,j:i32,k:f32}>>
54 // CHECK-LABEL: func.func @test_return_cptr(
55 // CHECK-SAME: %[[VAL_0:.*]]: !fir.ref<!fir.type<_QM__fortran_builtinsT__builtin_c_ptr{__address:i64}>>) {
56 // CHECK: %[[VAL_1:.*]] = fir.call @return_cptr() : () -> !fir.ref<none>
57 // CHECK: %[[VAL_2:.*]] = fir.field_index __address, !fir.type<_QM__fortran_builtinsT__builtin_c_ptr{__address:i64}>
58 // CHECK: %[[VAL_3:.*]] = fir.coordinate_of %[[VAL_0]], %[[VAL_2]] : (!fir.ref<!fir.type<_QM__fortran_builtinsT__builtin_c_ptr{__address:i64}>>, !fir.field) -> !fir.ref<i64>
59 // CHECK: %[[VAL_4:.*]] = fir.convert %[[VAL_1]] : (!fir.ref<none>) -> i64
60 // CHECK: fir.store %[[VAL_4]] to %[[VAL_3]] : !fir.ref<i64>