@@ -1360,6 +1360,30 @@ void complex_type_argument() {
13601360// OGCG: %[[TMP_ARG:.*]] = load <2 x float>, ptr %[[ARG_ADDR]], align 4
13611361// OGCG: call void @_Z22complex_type_parameterCf(<2 x float> noundef %[[TMP_ARG]])
13621362
1363+ float _Complex complex_type_return_type () {
1364+ return { 1 .0f , 2 .0f };
1365+ }
1366+
1367+ // CIR: %[[RET_ADDR:.*]] = cir.alloca !cir.complex<!cir.float>, !cir.ptr<!cir.complex<!cir.float>>, ["__retval"]
1368+ // CIR: %[[RET_VAL:.*]] = cir.const #cir.const_complex<#cir.fp<1.000000e+00> : !cir.float, #cir.fp<2.000000e+00> : !cir.float> : !cir.complex<!cir.float>
1369+ // CIR: cir.store{{.*}} %[[RET_VAL]], %[[RET_ADDR]] : !cir.complex<!cir.float>, !cir.ptr<!cir.complex<!cir.float>>
1370+ // CIR: %[[TMP_RET:.*]] = cir.load %[[RET_ADDR]] : !cir.ptr<!cir.complex<!cir.float>>, !cir.complex<!cir.float>
1371+ // CIR: cir.return %[[TMP_RET]] : !cir.complex<!cir.float>
1372+
1373+ // TODO(CIR): the difference between the CIR LLVM and OGCG is because the lack of calling convention lowering,
1374+ // LLVM: %[[RET_ADDR:.*]] = alloca { float, float }, i64 1, align 4
1375+ // LLVM: store { float, float } { float 1.000000e+00, float 2.000000e+00 }, ptr %[[RET_ADDR]], align 4
1376+ // LLVM: %[[TMP_RET:.*]] = load { float, float }, ptr %[[RET_ADDR]], align 4
1377+ // LLVM: ret { float, float } %[[TMP_RET]]
1378+
1379+ // OGCG: %[[RET_ADDR:.*]] = alloca { float, float }, align 4
1380+ // OGCG: %[[RET_VAL_REAL:.*]] = getelementptr inbounds nuw { float, float }, ptr %[[RET_ADDR]], i32 0, i32 0
1381+ // OGCG: %[[RET_VAL_IMAG:.*]] = getelementptr inbounds nuw { float, float }, ptr %[[RET_ADDR]], i32 0, i32 1
1382+ // OGCG: store float 1.000000e+00, ptr %[[RET_VAL_REAL]], align 4
1383+ // OGCG: store float 2.000000e+00, ptr %[[RET_VAL_IMAG]], align 4
1384+ // OGCG: %[[TMP_RET:.*]] = load <2 x float>, ptr %[[RET_ADDR]], align 4
1385+ // OGCG: ret <2 x float> %[[TMP_RET]]
1386+
13631387void real_on_scalar_bool () {
13641388 bool a;
13651389 bool b = __real__ a;
0 commit comments