LLVM 通过将整数转换为浮点数
Posted
技术标签:
【中文标题】LLVM 通过将整数转换为浮点数【英文标题】:LLVM pass converting integer to float 【发布时间】:2020-06-03 05:32:06 【问题描述】:我正在编写一个需要将整数类型转换为各种浮点类型的 LLVM 通道。我正在尝试使用 UIToFp 指令将整数值转换为浮点值。作为一个基本的测试用例,我使用类似于
的代码Value* promotedRandom = Builder.CreateUIToFP(ConstantInt::get(Type::getInt32Ty(M.getContext()), 4), Type::getFloatTy(M.getContext()));
其中 Builder 是我的函数的 IRBuilder 实例。但是由于某种原因,转换后这个值是 0 而不是 4,我可以通过打印值来确认。奇怪的是,如果 CreateUIToFP 的类型参数是 double 类型而不是 float 类型,则会打印 4 的正确答案。在下面的 UIToFP 文档中,我没有看到发生这种行为的任何原因。这个问题的原因是什么,应该如何解决。
将无符号整数常量转换为相应的浮点常量。 TYPE 必须是标量或向量浮点类型。 CST 必须是标量或向量整数类型。 CST 和 TYPE 都必须是标量,或相同数量元素的向量。
另外,如果我用 clang 编译这段代码
int main()
int test = 4;
float test2 = (float)test;
printf("%f\n", test2);
我收到以下说明
define dso_local i32 @main() #0
%1 = alloca i32, align 4
%2 = alloca float, align 4
store i32 4, i32* %1, align 4
%3 = load i32, i32* %1, align 4
%4 = sitofp i32 %3 to float
store float %4, float* %2, align 4
%5 = load float, float* %2, align 4
%6 = fpext float %5 to double
%7 = call i32 (i8*, ...) @printf(i8* getelementptr inbounds ([4 x i8], [4 x i8]* @.str, i64 0, i64 0), double %6)
ret i32 0
它显示了sitofp 和整数到浮点数的转换工作正常。尽管我使用的是 uitofp 而不是 sitofp,但我都尝试过,但都没有工作。
【问题讨论】:
将无符号整数转换为浮点数会牺牲精度。我猜零应该是 llvm 对精度损失或未定义行为的响应。 【参考方案1】:我发现问题在于 printf 没有将浮点数作为参数。当浮点数传递给 printf 时,它们被提升为双精度数。当我取浮点值并将其提升为双精度值时,代码可以正常工作。
【讨论】:
以上是关于LLVM 通过将整数转换为浮点数的主要内容,如果未能解决你的问题,请参考以下文章
将文本转换为浮点数/整数/日期时,Delphi 消息“您已插入无效值”