direct calls to inttoptr constants

I'm compiling code which contains indirect function calls
via their absolute addresses, which are known/fixed at compile-time:

pseudo c code:
int main() {
int (* f)(int) = (int (*)(int))12345678;
return (*f)(0);

the IR looks like:
define i32 @main() nounwind {
%0 = tail call i32 inttoptr (i64 12345678 to i32 (i32)*)(i32 0) nounwind
ret i32 %0

on X86 llc 2.4 compiles this to:
.align 16
.globl main
.type main,@function
subl $4, %esp
movl $0, (%esp)
movl $12345678, %eax
call *%eax
addl $4, %esp
.size main, .-main

.section .note.GNU-stack,"",@progbits

take a look at:
movl $12345678, %eax
call *%eax

does anyone know a way to cause llc to call the address directly?
hints where to start patching the codegen are also welcome.

expected assembly:
call *12345678

best regards


I'm doing something similar (I use LLVM as part of my JIT compiler) and
if I remember correctly, LLVM does the correct thing.

I think you need to try changing the i64 value to an i32 value.
If that doesn't work you could also try replacing the tail call with a normal call.


Tobias wrote:

Hello Mark,

I've followed your advice and changed the IR to:
%0 = call i32 inttoptr (i32 12345678 to i32 (i32)*)(i32 0) nounwind
the call is still indirect.

IMHO llc does not call it directly because the address is neither
a globalvalue (JIT) nor a external symbol.
That's why it uses a fallback mechanism to call it indirectly
assuming the address is not constant and is calculated at runtime.


Mark wrote:

I've looked into this a bit more.
You are right.
The confusion arose as I have two versions of my compiler:
The ahead-of-time compiler uses symbolic info and does the right thing.
The JIT compiler uses runtime addresses (in effect integers) and
when I examined the code in the debugger I found that LLVM produces indirect calls, like this:
mov $0x8153c8c,%eax
call *%eax

Sadly, however, I have no idea how to fix this :frowning:
but I will try and investigate.

Do you have any ideas yet?


Tobias wrote:

It's a instruction selection issue. Please file a bugzilla with a test case. Thanks.