Немного работы со стеком
Вот пример:
template<typename ptr_func >
class SFunc
{
private:
ptr_func _ptr;
public:
SFunc(ptr_func Function) : _ptr(Function) {}
operator ptr_func() { return _ptr; }
};
int _tmain(int argc, _TCHAR* argv[])
{
typedef int (*type_MessageBox)(HWND, LPCTSTR, LPCTSTR, UINT);
SFunc<type_MessageBox> MsgBox((type_MessageBox)MessageBox);
MsgBox(NULL, TEXT("HEllo"), NULL, NULL);
return 0;
}
При выполнее return приграмма падает. Если продизассемблировать то функция _tmain выглядит так:
push 0 ; uType
push 0 ; lpCaption
push offset Text ; "HEllo"
push 0 ; hWnd
call ds:__imp__MessageBoxW@16 ; MessageBoxW(x,x,x,x)
add esp, 10h ; <== Компилятор че то недопонял и пытается востановить стек
; Хотя выполняемая функции за собой все чистит
xor eax, eax
retn
Вопрос в том как отучить компилятор от этого безобразия.
Заранее благодарен.
PS: Это всего пример на самом деле код гораздо сложнее, но принцип ошибки такой.
Цитата: Ivan_Cheremisov
Может кто-нить знает можно ли в компиляторе VC 2005 отключить излишнюю заботливость о стеке.
Вопрос в том как отучить компилятор от этого безобразия.
Заранее благодарен.
PS: Это всего пример на самом деле код гораздо сложнее, но принцип ошибки такой.
Вопрос в том как отучить компилятор от этого безобразия.
Заранее благодарен.
PS: Это всего пример на самом деле код гораздо сложнее, но принцип ошибки такой.
"Плюю в потолок попадаю на себя. Вопрос в том как отучить гравитацию от этого безобразия."
Не компилятор надо отучать, а самому писать правильно.
Определение функции MwssageBoxA
Код:
int WINAPI MessageBox(HWND hWnd, LPCTSTR lpText, LPCTSTR lpCaption, UINT uType);
смотрим определение типа твоего указателя
Код:
typedef int (*type_MessageBox)(HWND, LPCTSTR, LPCTSTR, UINT);
чего-то нехватает... а именно
Код:
typedef int (WINAPI *type_MessageBox)(HWND, LPCTSTR, LPCTSTR, UINT);
Помнится, однажды я писал пакет. Так при создании программы, линковщик "не видел" функции из пакета, потому что случайно для этих проектов назначил разные "умолчания" :(. Соответственно, в пакете получились функции типа __stdcall, а программе требовались совсем другие.
Спасибо. Действительно глупая ошибка.