This function generates the following asm under -O3 in version 4.5 #include <stdarg.h> void va_overload2(int p1, int p2); void va_overload3(int p1, int p2, int p3);
void va_overload(int p1, int p2, ...) { if (p2 == 7) { va_list v; va_start(v, p2); int p3 = va_arg(v, int); va_end(v); va_overload3(p1, p2, p3); return; } va_overload2(p1, p2); } Dump of assembler code for function va_overload: 0x0000000000400520 <+0>: sub $0x58,%rsp 0x0000000000400524 <+4>: cmp $0x7,%esi 0x0000000000400527 <+7>: mov %rdx,0x30(%rsp) 0x000000000040052c <+12>: je 0x400540 <va_overload+32> 0x000000000040052e <+14>: callq 0x4004f0 <va_overload2> 0x0000000000400533 <+19>: add $0x58,%rsp 0x0000000000400537 <+23>: retq 0x0000000000400538 <+24>: nopl 0x0(%rax,%rax,1) 0x0000000000400540 <+32>: lea 0x60(%rsp),%rax 0x0000000000400545 <+37>: mov 0x30(%rsp),%edx 0x0000000000400549 <+41>: movl $0x18,(%rsp) 0x0000000000400550 <+48>: mov %rax,0x8(%rsp) 0x0000000000400555 <+53>: lea 0x20(%rsp),%rax 0x000000000040055a <+58>: mov %rax,0x10(%rsp) 0x000000000040055f <+63>: callq 0x400500 <va_overload3> 0x0000000000400564 <+68>: add $0x58,%rsp 0x0000000000400568 <+72>: retq This could be replaced with the much more compact: cmp $0x7, %esi je 1f jmp va_overload2 1: jmp va_overload3 since the third parameter is passed in a register, and will still be there after the comparison. (Actually, if it were passed on the stack it still wouldn't matter, because we can tail-call here.) -- Summary: va_list usage missed optimization. Product: gcc Version: 4.5.0 Status: UNCONFIRMED Severity: enhancement Priority: P3 Component: c AssignedTo: unassigned at gcc dot gnu dot org ReportedBy: svfuerst at gmail dot com GCC build triplet: x86_64-linux GCC host triplet: x86_64-linux GCC target triplet: x86_64-linux http://gcc.gnu.org/bugzilla/show_bug.cgi?id=44262