![]() |
Модераторы: Poseidon, Snowy, bems, MetalFan |
![]() ![]() ![]() |
|
BofA |
|
||||||||
Новичок Профиль Группа: Участник Сообщений: 10 Регистрация: 7.7.2006 Репутация: нет Всего: нет |
Доброго времени суток, дорогие друзья! Требуется ваша помощь.
Итак, имеется DLL (исходников DLL нет), которая экспортирует следующую функцию:
где STATUS_CALLBACK объявлена как
Непосредственно в моей программе имеется класс
Соответственно в конструкторе класса хочется написать что-то вроде
дабы объяснить DLLке, что в качестве callback функции нужно использовать классовую функцию StatusCallback, но компилятор закономерно выдаёт "Incompatible types: 'regular procedure and method pointer'". Соответственно, если объявлять функцию StatusCallback вне класса, то всё работает, но этот вариант не подходит. Поскольку исходников DLL нет, то дописать "of object" к объявлению типа STATUS_CALLBACK невозможно. Посему подскажите пожалуйста, как можно разрешить данную проблему и передать классовый метод StatusCallback как обычную функцию. |
||||||||
|
|||||||||
MetalFan |
|
|||
![]() Аццкий Сотона ![]() ![]() ![]() ![]() Профиль Группа: Комодератор Сообщений: 3815 Регистрация: 2.10.2006 Где: Moscow Репутация: 62 Всего: 128 |
имхо невозможно в данном случае. ибо первым параметром в процедуру-метод неявно передается ссылка на объект.
-------------------- There are always someone smarter than you... |
|||
|
||||
Rennigth |
|
||||
![]() Эксперт ![]() ![]() ![]() Профиль Группа: Участник Клуба Сообщений: 1708 Регистрация: 21.6.2004 Где: Moscow Репутация: 49 Всего: 76 |
BofA,
Попробуй передавать так:
Может проглотит... Добавлено через 3 минуты и 10 секунд туплю, перепутал, немного не так, ща... ![]() Добавлено через 6 минут и 10 секунд
Не проверял правда ![]() -------------------- (* Honesta mors turpi vita potior *) |
||||
|
|||||
BofA |
|
|||
Новичок Профиль Группа: Участник Сообщений: 10 Регистрация: 7.7.2006 Репутация: нет Всего: нет |
MetalFan
Надежда умирает последней ![]() ![]() Rennigth, Компилятор ругается на преобразование TMethod(StatusCallback) - говорит "Invalid typecast" ![]() Это сообщение отредактировал(а) BofA - 7.5.2008, 13:19 |
|||
|
||||
Rennigth |
|
|||
![]() Эксперт ![]() ![]() ![]() Профиль Группа: Участник Клуба Сообщений: 1708 Регистрация: 21.6.2004 Где: Moscow Репутация: 49 Всего: 76 |
BofA, а так:
? -------------------- (* Honesta mors turpi vita potior *) |
|||
|
||||
BofA |
|
|||
Новичок Профиль Группа: Участник Сообщений: 10 Регистрация: 7.7.2006 Репутация: нет Всего: нет |
Rennigth,
Получился весьма интересный эффект ![]() Программа компилируется, DLL осознаёт, что надо использовать StatusCallback, но когда происходит событие и DLLка вызывает эту функцию, то а) переменные не передаются (все равны нулю) б) возникает Access violation Ради эксперимента убрал stdcall у StatusCallback, и переменные почему-то начали передаваться, но Access violation остался. P.S.: StatusCallback выглядит так
Ставлю точку останова на единственной строчке процедуры, эта строчка отрабатывает, а после этого вылезает Access violation. |
|||
|
||||
MetalFan |
|
|||
![]() Аццкий Сотона ![]() ![]() ![]() ![]() Профиль Группа: Комодератор Сообщений: 3815 Регистрация: 2.10.2006 Где: Moscow Репутация: 62 Всего: 128 |
Rennigth, я уже говорил, что при вызове метода первым неявным параметром должен идти указатель на объект.
это происходит потому, что вместо ожидаемого указателя на объект приходит черте-че (nConnectionEvent), соотв Self не доступен и все параметры сдвинуты. -------------------- There are always someone smarter than you... |
|||
|
||||
BofA |
|
|||
Новичок Профиль Группа: Участник Сообщений: 10 Регистрация: 7.7.2006 Репутация: нет Всего: нет |
MetalFan,
Неужели сие никак нельзя обойти? Наверняка ведь должен быть способ подсунуть этот самый "первый неявный параметр"? |
|||
|
||||
MetalFan |
|
|||
![]() Аццкий Сотона ![]() ![]() ![]() ![]() Профиль Группа: Комодератор Сообщений: 3815 Регистрация: 2.10.2006 Где: Moscow Репутация: 62 Всего: 128 |
з.ы. в свое время мне понадобилось следующее: поставить обработчиком события не метод класса, а просто процедуру.
сделано было что-то типа:
-------------------- There are always someone smarter than you... |
|||
|
||||
Rennigth |
|
|||
![]() Эксперт ![]() ![]() ![]() Профиль Группа: Участник Клуба Сообщений: 1708 Регистрация: 21.6.2004 Где: Moscow Репутация: 49 Всего: 76 |
м.б. сейчас лезь смотреть что обязательно должно передаваться нехочется, но вот такой финт ушами проходит без проблем, думаю что и тут можно выкрутиться... Добавлено через 42 секунды MetalFan, я про тоже ![]() -------------------- (* Honesta mors turpi vita potior *) |
|||
|
||||
BofA |
|
|||
Новичок Профиль Группа: Участник Сообщений: 10 Регистрация: 7.7.2006 Репутация: нет Всего: нет |
Основная проблема в том, что нет доступа к функции SET_CALLBACK, описанной в DLL. В описанных же Вами примерах был доступ к той функции, которая занимается непосредственно присвоением метода, поэтому простор для экспериментов был больше. Здесь же я не могу объяснить функции SET_CALLBACK, что ей передаётся метод, где первым идёт неявный параметр - указатель, поэтому SET_CALLBACK тупо забивает в этот неявный параметр то, что должно было попасть, например, в nConnectionEvent ( MetalFan, я правильно понимаю? ) Неужели данная проблема действительно не имеет решения?
|
|||
|
||||
MetalFan |
|
|||
![]() Аццкий Сотона ![]() ![]() ![]() ![]() Профиль Группа: Комодератор Сообщений: 3815 Регистрация: 2.10.2006 Где: Moscow Репутация: 62 Всего: 128 |
если исходники DLL недоступны, то имхо таким способом не выйдет... -------------------- There are always someone smarter than you... |
|||
|
||||
dumb |
|
|||
![]() sceloglauxalbifacies ![]() ![]() ![]() ![]() Профиль Группа: Экс. модератор Сообщений: 2929 Регистрация: 16.6.2006 Репутация: 13 Всего: 158 |
через "переходник" можно сделать: смотреть здесь на реализацию TLiteFrame.Create
|
|||
|
||||
BofA |
|
|||
Новичок Профиль Группа: Участник Сообщений: 10 Регистрация: 7.7.2006 Репутация: нет Всего: нет |
dumb,
К сожалению, я не знаю ассемблера ![]() Не могли бы Вы чуть подробнее осветить данный вопрос? |
|||
|
||||
dumb |
|
|||
![]() sceloglauxalbifacies ![]() ![]() ![]() ![]() Профиль Группа: Экс. модератор Сообщений: 2929 Регистрация: 16.6.2006 Репутация: 13 Всего: 158 |
там не обязательно знать ассемблер. просто "слизывай" реализацию установки call-back'а.
|
|||
|
||||
Snowy |
|
|||
![]() Эксперт ![]() ![]() ![]() ![]() Профиль Группа: Модератор Сообщений: 11363 Регистрация: 13.10.2004 Где: Питер Репутация: 192 Всего: 484 |
Функция чисто процедурная.
Поэтому не имеет понятия, какой объект её вызвал. Она вызывает колбэк по конкретному адресу. Поэтому использовать её можно только в синглтоне (единственный экземпляр класса, обычно глобальная переменная), либо выстраивать строгую очередь вызовов - объект делает вызов и запрещает повторные вызовы до получения колбэка (либо сам, либо используется специальных мэнеджер списка объектов этого класса). Вобщем, без дополнительного костыля, процедурную схему в объектную не встроить. Можно построить специальный мэнеджер-обёртку. Который будет принимать вызовы, заносить в список объект, который произвёл вызов, а по колбэку доставать его из списка и делать вызов к нему. Такой мэнеджер можно сделать скрытым и все обращения к нему производить через сам объект. Вобщем, либо синглтон, либо дополнительный мэнеджер, обслуживающий очередь вызовов. |
|||
|
||||
![]() ![]() ![]() |
Правила форума "Delphi: Общие вопросы" | |
|
Запрещается! 1. Публиковать ссылки на вскрытые компоненты 2. Обсуждать взлом компонентов и делиться вскрытыми компонентами
Если Вам понравилась атмосфера форума, заходите к нам чаще! С уважением, Snowy, MetalFan, bems, Poseidon, Rrader. |
1 Пользователей читают эту тему (1 Гостей и 0 Скрытых Пользователей) | |
0 Пользователей: | |
« Предыдущая тема | Delphi: Общие вопросы | Следующая тема » |
|
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности Powered by Invision Power Board(R) 1.3 © 2003 IPS, Inc. |