Я пишу некоторый низкоуровневый код, и я заметил некоторый ненужный уровень косвенности вызова функции, и я просто не понимаю, в чем причина этой косвенности.Вот фиктивный код, который показывает это поведение:
__declspec(noinline) int get_alignment(void * ptr)
{
return 1;
}
__declspec(noinline) int test123()
{
char buf[123];
return get_alignment(buf);
}
Затем, когда я перехожу код внутри функции test () в отладчике в режиме asm (Ctrl + F11), я вижу это:
__declspec(noinline) int test123()
{
0041FA70 sub esp,7Ch
char buf[123];
return get_alignment(buf);
0041FA73 lea eax,[esp]
0041FA76 push eax
0041FA77 call get_alignment (40A38Fh)
}
...
get_alignment:
0040A38F jmp get_alignment (41FA60h)
...
__declspec(noinline) int get_alignment(void * ptr)
{
return 1;
0041FA60 mov eax,1
}
Итак, вопрос об этом дополнительном уровне косвенности: get_alignment: 0040A38F jmp get_alignment (41FA60h)
WTF это о чем ?!Я просто не понимаю, это не импортированная функция из dll, это локальная функция, определенная в исполняемом файле.Этот исполняемый файл скомпилирован со всеми видами оптимизаций (кроме генерации временного кода ссылки).Если я добавлю static
к объявлению этого get_alignment, то эта дополнительная косвенность исчезнет.Но я не ищу «исправления», я просто хотел понять, почему этот дополнительный переход вообще существует!
В моем реальном приложении я фактически использую функцию, написанную в файле .asm, и я простоне понимаю, почему генерируется дополнительный прыжок.Похоже, что если я скомпилирую свой код в C-режиме (не в C ++), то я больше не вижу такого уровня косвенности ...
Кто-нибудь может пролить свет на это странное поведение?
Спасибо!