Function pointers bitcasted to varargs

Hi all,

I had the following function that used function pointers with void arguments,

typedef void (*FP)();

void foo() {
  printf("hello world from foo\n");
}
int main() {
  FP fp;
  fp = foo;
  (*fp)();

}

The corresponding bitcode, with no optimizations is

target datalayout =
"e-p:64:64:64-i1:8:8-i8:8:8-i16:16:16-i32:32:32-i64:64:64-f32:32:32-f64:64:64-v64:64:64-v128:128:128-a0:0:64-s0:64:64-f80:128:128"
target triple = "x86_64-unknown-linux-gnu"

@.str = private constant [21 x i8] c"hello world from foo\00", align 1
; <[21 x i8]*> [#uses=1]

define void @foo() nounwind {
entry:
  %0 = call i32 @puts(i8* getelementptr inbounds ([21 x i8]* @.str,
i64 0, i64 0)) nounwind ; <i32> [#uses=0]
  br label %return

return: ; preds = %entry
  ret void
}

declare i32 @puts(i8*)

define i32 @main() nounwind {
entry:
  %retval = alloca i32 ; <i32*> [#uses=1]
  %fp = alloca void (...)* ; <void (...)**> [#uses=2]
  %"alloca point" = bitcast i32 0 to i32 ; <i32> [#uses=0]
  store void (...)* bitcast (void ()* @foo to void (...)*), void
(...)** %fp, align 8
  %0 = load void (...)** %fp, align 8 ; <void (...)*> [#uses=1]
  call void (...)* %0() nounwind
  br label %return

return: ; preds = %entry
  %retval1 = load i32* %retval ; <i32> [#uses=1]
  ret i32 %retval1
}

I was wondering why LLVM casts the function pointer to a varargs
function?Is there some reason why it should do that?

Thanks.
Arushi

Do you compile this as C? In C, unlike in C++, empty parenthesis do
not mean "no arguments", they mean "no prototype", which is typically
treated the same way as varargs in calling conventions. To declare
function with no arguments do typedef void (*FP)(void);

Eugene

Thanks!.

Arushi