Skip to content

Commit f818f4c

Browse files
authored
Simplify fcmp intrinsic logic for AOT/XIP (bytecodealliance#1881)
1 parent 219713b commit f818f4c

File tree

1 file changed

+39
-60
lines changed

1 file changed

+39
-60
lines changed

core/iwasm/compilation/aot_emit_conversion.c

Lines changed: 39 additions & 60 deletions
Original file line numberDiff line numberDiff line change
@@ -9,35 +9,47 @@
99
#include "../aot/aot_intrinsic.h"
1010
#include "../aot/aot_runtime.h"
1111

12-
static bool
13-
trunc_float_to_int(AOTCompContext *comp_ctx, AOTFuncContext *func_ctx,
14-
LLVMValueRef operand, LLVMTypeRef src_type,
15-
LLVMTypeRef dest_type, LLVMValueRef min_value,
16-
LLVMValueRef max_value, char *name, bool sign)
12+
static LLVMValueRef
13+
call_fcmp_intrinsic(AOTCompContext *comp_ctx, AOTFuncContext *func_ctx,
14+
enum AOTFloatCond cond, LLVMRealPredicate op,
15+
LLVMValueRef lhs, LLVMValueRef rhs, LLVMTypeRef src_type,
16+
const char *name)
1717
{
18-
LLVMBasicBlockRef check_nan_succ, check_overflow_succ;
19-
LLVMValueRef is_less, is_greater, res;
20-
18+
LLVMValueRef res = NULL;
2119
if (comp_ctx->disable_llvm_intrinsics
2220
&& aot_intrinsic_check_capability(
2321
comp_ctx, src_type == F32_TYPE ? "f32_cmp" : "f64_cmp")) {
2422
LLVMTypeRef param_types[3];
25-
LLVMValueRef opcond = LLVMConstInt(I32_TYPE, FLOAT_UNO, true);
23+
LLVMValueRef opcond = LLVMConstInt(I32_TYPE, cond, true);
2624
param_types[0] = I32_TYPE;
2725
param_types[1] = src_type;
2826
param_types[2] = src_type;
2927
res = aot_call_llvm_intrinsic(
3028
comp_ctx, func_ctx, src_type == F32_TYPE ? "f32_cmp" : "f64_cmp",
31-
I32_TYPE, param_types, 3, opcond, operand, operand);
29+
I32_TYPE, param_types, 3, opcond, lhs, rhs);
3230
if (!res) {
3331
goto fail;
3432
}
3533
res = LLVMBuildIntCast(comp_ctx->builder, res, INT1_TYPE, "bit_cast");
3634
}
3735
else {
38-
res = LLVMBuildFCmp(comp_ctx->builder, LLVMRealUNO, operand, operand,
39-
"fcmp_is_nan");
36+
res = LLVMBuildFCmp(comp_ctx->builder, op, lhs, rhs, name);
4037
}
38+
fail:
39+
return res;
40+
}
41+
42+
static bool
43+
trunc_float_to_int(AOTCompContext *comp_ctx, AOTFuncContext *func_ctx,
44+
LLVMValueRef operand, LLVMTypeRef src_type,
45+
LLVMTypeRef dest_type, LLVMValueRef min_value,
46+
LLVMValueRef max_value, char *name, bool sign)
47+
{
48+
LLVMBasicBlockRef check_nan_succ, check_overflow_succ;
49+
LLVMValueRef is_less, is_greater, res;
50+
51+
res = call_fcmp_intrinsic(comp_ctx, func_ctx, FLOAT_UNO, LLVMRealUNO,
52+
operand, operand, src_type, "fcmp_is_nan");
4153

4254
if (!res) {
4355
aot_set_last_error("llvm build fcmp failed.");
@@ -58,54 +70,18 @@ trunc_float_to_int(AOTCompContext *comp_ctx, AOTFuncContext *func_ctx,
5870
check_nan_succ)))
5971
goto fail;
6072

61-
if (comp_ctx->disable_llvm_intrinsics
62-
&& aot_intrinsic_check_capability(
63-
comp_ctx, src_type == F32_TYPE ? "f32_cmp" : "f64_cmp")) {
64-
LLVMTypeRef param_types[3];
65-
LLVMValueRef opcond = LLVMConstInt(I32_TYPE, FLOAT_LE, true);
66-
param_types[0] = I32_TYPE;
67-
param_types[1] = src_type;
68-
param_types[2] = src_type;
69-
is_less = aot_call_llvm_intrinsic(
70-
comp_ctx, func_ctx, src_type == F32_TYPE ? "f32_cmp" : "f64_cmp",
71-
I32_TYPE, param_types, 3, opcond, operand, min_value);
72-
if (!is_less) {
73-
goto fail;
74-
}
75-
is_less =
76-
LLVMBuildIntCast(comp_ctx->builder, is_less, INT1_TYPE, "bit_cast");
77-
}
78-
else {
79-
is_less = LLVMBuildFCmp(comp_ctx->builder, LLVMRealOLE, operand,
80-
min_value, "fcmp_min_value");
81-
}
73+
is_less =
74+
call_fcmp_intrinsic(comp_ctx, func_ctx, FLOAT_LE, LLVMRealOLE, operand,
75+
min_value, src_type, "fcmp_min_value");
8276

8377
if (!is_less) {
8478
aot_set_last_error("llvm build fcmp failed.");
8579
goto fail;
8680
}
8781

88-
if (comp_ctx->disable_llvm_intrinsics
89-
&& aot_intrinsic_check_capability(
90-
comp_ctx, src_type == F32_TYPE ? "f32_cmp" : "f64_cmp")) {
91-
LLVMTypeRef param_types[3];
92-
LLVMValueRef opcond = LLVMConstInt(I32_TYPE, FLOAT_GE, true);
93-
param_types[0] = I32_TYPE;
94-
param_types[1] = src_type;
95-
param_types[2] = src_type;
96-
is_greater = aot_call_llvm_intrinsic(
97-
comp_ctx, func_ctx, src_type == F32_TYPE ? "f32_cmp" : "f64_cmp",
98-
I32_TYPE, param_types, 3, opcond, operand, max_value);
99-
if (!is_greater) {
100-
goto fail;
101-
}
102-
is_greater = LLVMBuildIntCast(comp_ctx->builder, is_greater, INT1_TYPE,
103-
"bit_cast");
104-
}
105-
else {
106-
is_greater = LLVMBuildFCmp(comp_ctx->builder, LLVMRealOGE, operand,
107-
max_value, "fcmp_min_value");
108-
}
82+
is_greater =
83+
call_fcmp_intrinsic(comp_ctx, func_ctx, FLOAT_GE, LLVMRealOGE, operand,
84+
max_value, src_type, "fcmp_min_value");
10985

11086
if (!is_greater) {
11187
aot_set_last_error("llvm build fcmp failed.");
@@ -183,8 +159,9 @@ trunc_sat_float_to_int(AOTCompContext *comp_ctx, AOTFuncContext *func_ctx,
183159
LLVMValueRef zero = (dest_type == I32_TYPE) ? I32_ZERO : I64_ZERO;
184160
LLVMValueRef vmin, vmax;
185161

186-
if (!(res = LLVMBuildFCmp(comp_ctx->builder, LLVMRealUNO, operand, operand,
187-
"fcmp_is_nan"))) {
162+
if (!(res =
163+
call_fcmp_intrinsic(comp_ctx, func_ctx, FLOAT_UNO, LLVMRealUNO,
164+
operand, operand, src_type, "fcmp_is_nan"))) {
188165
aot_set_last_error("llvm build fcmp failed.");
189166
goto fail;
190167
}
@@ -212,8 +189,9 @@ trunc_sat_float_to_int(AOTCompContext *comp_ctx, AOTFuncContext *func_ctx,
212189

213190
/* Start to translate check_nan_succ block */
214191
LLVMPositionBuilderAtEnd(comp_ctx->builder, check_nan_succ);
215-
if (!(is_less = LLVMBuildFCmp(comp_ctx->builder, LLVMRealOLE, operand,
216-
min_value, "fcmp_min_value"))) {
192+
if (!(is_less = call_fcmp_intrinsic(comp_ctx, func_ctx, FLOAT_LE,
193+
LLVMRealOLE, operand, min_value,
194+
src_type, "fcmp_min_value"))) {
217195
aot_set_last_error("llvm build fcmp failed.");
218196
goto fail;
219197
}
@@ -232,8 +210,9 @@ trunc_sat_float_to_int(AOTCompContext *comp_ctx, AOTFuncContext *func_ctx,
232210

233211
/* Start to translate check_less_succ block */
234212
LLVMPositionBuilderAtEnd(comp_ctx->builder, check_less_succ);
235-
if (!(is_greater = LLVMBuildFCmp(comp_ctx->builder, LLVMRealOGE, operand,
236-
max_value, "fcmp_max_value"))) {
213+
if (!(is_greater = call_fcmp_intrinsic(comp_ctx, func_ctx, FLOAT_GE,
214+
LLVMRealOGE, operand, max_value,
215+
src_type, "fcmp_max_value"))) {
237216
aot_set_last_error("llvm build fcmp failed.");
238217
goto fail;
239218
}

0 commit comments

Comments
 (0)