c - How to configure the call style for DLL imports using GCC (mingw64)? - Stack Overflow

Building the following test program using GCC:#include <windows.h>int main() {Sleep(1);return 0

Building the following test program using GCC:

#include <windows.h>
int main() {
    Sleep(1);
    return 0;
}
gcc -m64 -o main.exe main.c

In the resulting binary, the Sleep function is called in this manner:

mov rax, [<Sleep>]
call rax

where <Sleep> is an address in the .idata section.

Is there a way to make gcc generate the call without using a register? I'd also be interested to know why it chooses to use two instructions here.


For comparison, the same program compiled using MSVC: cl main.c, which yields the following:

call [<Sleep>]

where <Sleep> is an address in the .rdata section.

I also tried Clang: clang -o main.exe main.c, which gives the same result as MSVC.

Compiler versions in my environment:

gcc version 14.2.0 (MinGW-W64 x86_64-ucrt-posix-seh)

Microsoft (R) C/C++ Optimizing Compiler Version 19.43.34809 for x64

clang version 18.1.8, Target: x86_64-pc-windows-msvc

Building the following test program using GCC:

#include <windows.h>
int main() {
    Sleep(1);
    return 0;
}
gcc -m64 -o main.exe main.c

In the resulting binary, the Sleep function is called in this manner:

mov rax, [<Sleep>]
call rax

where <Sleep> is an address in the .idata section.

Is there a way to make gcc generate the call without using a register? I'd also be interested to know why it chooses to use two instructions here.


For comparison, the same program compiled using MSVC: cl main.c, which yields the following:

call [<Sleep>]

where <Sleep> is an address in the .rdata section.

I also tried Clang: clang -o main.exe main.c, which gives the same result as MSVC.

Compiler versions in my environment:

gcc version 14.2.0 (MinGW-W64 x86_64-ucrt-posix-seh)

Microsoft (R) C/C++ Optimizing Compiler Version 19.43.34809 for x64

clang version 18.1.8, Target: x86_64-pc-windows-msvc

Share Improve this question asked Mar 20 at 15:02 CauteriteCauterite 1,71318 silver badges24 bronze badges 3
  • 2 Sure, you can just turn on the optimizer. – Ian Abbott Commented Mar 20 at 16:05
  • I tried using the -fno-function-cse optimiser setting (description: "Do not put function addresses in registers"), however it made no difference. – Cauterite Commented Mar 21 at 11:27
  • Try the -O option. I'll undelete the answer I deleted earlier just in case it is useful. – Ian Abbott Commented Mar 21 at 14:55
Add a comment  | 

1 Answer 1

Reset to default 1

This behavior looks like it should be controlled by the -ffunction-cse or -fno-function-cse option:

-fno-function-cse

Do not put function addresses in registers; make each instruction that calls a constant function contain the function’s address explicitly.

This option results in less efficient code, but some strange hacks that alter the assembler output may be confused by the optimizations performed when this option is not used.

The default is -ffunction-cse

However, for x86, the -fno-function-cse option does not seem to have the desired effect of calling the when PC-relative addressing is in use, but turning on optimization with the -O option (except for -O0 which turns off optimization) does have the desired effect of calling the function's (PC-relative) address explicitly. Note that in both cases, it is the function's import stub function that is called, since the real function's address in the DLL is not known to the linker.

发布者:admin,转转请注明出处:http://www.yc00.com/questions/1744401241a4572398.html

相关推荐

发表回复

评论列表(0条)

  • 暂无评论

联系我们

400-800-8888

在线咨询: QQ交谈

邮件:admin@example.com

工作时间:周一至周五,9:30-18:30,节假日休息

关注微信