Модераторы: feodorv, GremlinProg, xvr, Fixin
  

Поиск:

Ответ в темуСоздание новой темы Создание опроса
> thunk для dde, thunk на asm для dde callback 
:(
    Опции темы
kichum
Дата 16.4.2012, 10:33 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 9
Регистрация: 17.10.2008

Репутация: нет
Всего: нет



Здравствуйте. Столкнулся с проблемой написания Dde сервера. При инициализации нужно указать PFNCALLBACK, но функция является методом класса (DDESrv) и делать ее статической не хочется. Нашел на просторах интернета пример thunk, который я благополучно использовал, но выявилась проблема: входные параметры как будто сдвинуты влево (запускал без переходника и спереходником. входные параметры похожи на вызов без переходника но кажется что uType = uFmt, uFmt = hconv и т.д. { более понятно не смог обьяснить }).

Вот это я взял из сети:
Код

#pragma once

#include <windows.h> 

#pragma pack(push,1) 
struct _ProcThunk 
{ 
    DWORD   m_mov;          
    DWORD   m_this;          
    BYTE    m_jmp;          
    DWORD   m_relproc;      
}; 
#pragma pack(pop) 

class ProcThunk 
{ 
public: 
    union 
    { 
        _ProcThunk thunk; 
    }; 
    void Init(void* proc, void* pThis) 
    { 
        thunk.m_mov = 0x042444C7; 
        thunk.m_this = (DWORD)pThis; 
        thunk.m_jmp = 0xe9; 
        thunk.m_relproc = (int)proc - ((int)this+sizeof(_ProcThunk)); 
        FlushInstructionCache(GetCurrentProcess(), &thunk, sizeof(thunk)); 
    }

}; 

__declspec (naked) void* _cdecl pvoid_cast(...) 
{ 
    _asm 
    { 
        mov eax, [esp+4h] 
        ret 
    } 
}



а так я это использую:
Код


    m_ProcThunk.Init(pvoid_cast(&CDDESrv::fnCallBack), (void*)this);


    if (s_dwIdInst == NULL) {
        m_uiError = DdeInitialize(&s_dwIdInst, (PFNCALLBACK)&(m_ProcThunk.thunk), APPCLASS_STANDARD, NULL);
        if (m_uiError != DMLERR_NO_ERROR)
            return;
    }


Вот прототип колбека (чтобы было понятно что там с параметрами):
Код

HDDEDATA CALLBACK fnCallBack(UINT uType, UINT uFmt, HCONV hconv, 
        HSZ hsz1, HSZ hsz2, HDDEDATA hdata, DWORD dwData1, DWORD dwData2);


Может это не универсальный переходник или я что-то не так делаю, но в асме я плох.
Может что-то в стеке не так или еще что? Прошу помощи.
PM MAIL   Вверх
Akira
Дата 16.4.2012, 10:45 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 45
Регистрация: 26.3.2012

Репутация: нет
Всего: нет



Сути проблемы я если честно не понял (не выспался) но возможно проблема из за calling conventions... __cdecl, __stdcall
Залей скомпиленный сэмпл.

Это сообщение отредактировал(а) Akira - 16.4.2012, 10:48
PM MAIL   Вверх
kichum
Дата 16.4.2012, 11:16 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 9
Регистрация: 17.10.2008

Репутация: нет
Всего: нет



Семпл - пример? Если да, то прикрепляю скомпилированный в Debug на VC++2010

Присоединённый файл ( Кол-во скачиваний: 3 )
Присоединённый файл  tmp.rar 9,13 Kb
PM MAIL   Вверх
xvr
Дата 16.4.2012, 12:23 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Комодератор
Сообщений: 7046
Регистрация: 28.8.2007
Где: Дублин, Ирландия

Репутация: 40
Всего: 223



Во первых - ваш thunk использует вполне конкретный calling conversion для вызова, и не факт, что VS использует тот же. Во вторых, ваш pvoid_cast предполагает, что размер void* и указателя на метод совпадают, что так же может не соотвествовать действительности

Цитата(kichum @  16.4.2012,  10:33 Найти цитируемый пост)
и делать ее статической не хочется.

Почему? Обычно так и делают. (Точнее делают статический переходник, который вызывает функцию класса. А this ему передают в глобале)


Это сообщение отредактировал(а) xvr - 16.4.2012, 12:23
PM MAIL   Вверх
kichum
Дата 16.4.2012, 12:30 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Новичок



Профиль
Группа: Участник
Сообщений: 9
Регистрация: 17.10.2008

Репутация: нет
Всего: нет



xvr, да, возможно так и правильнее сделать и если не сложно, подскажите поподробнее. Вот у меня библиотечная функция инициализации. Я не могу передать ей параметров больше или меньше, чем задано (т.е. указатель this я передать не могу). Т.к. объектов класса может быть больше чем один (класс не синглтон) то как передать ей этот указатель this если не делать каждый обьект класса глобальным?


Это сообщение отредактировал(а) kichum - 16.4.2012, 12:45
PM MAIL   Вверх
xvr
Дата 16.4.2012, 12:43 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Комодератор
Сообщений: 7046
Регистрация: 28.8.2007
Где: Дублин, Ирландия

Репутация: 40
Всего: 223



Цитата(kichum @  16.4.2012,  12:30 Найти цитируемый пост)
Т.к. объектов класса может быть больше чем один (класс не синглтон)

У вас количество этих объектов фиксированное? Т.е. можно заранее сказать, что их не будет больше, чем N (некая константа)? 
Далее, формат этих функций фиксирован? Т.е. можно заранее прописать все нужные наборы параметров?
Если да, то этот вопрос решается довольно просто (и без ассемблерных thunk'ов)

PM MAIL   Вверх
GremlinProg
Дата 17.4.2012, 07:12 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Комодератор
Сообщений: 2706
Регистрация: 9.8.2005
Где: Тюмень

Репутация: 99
Всего: 106



судя по прототипам, не очень продуманный API (по всей видимости, интерфейс вымирающий),
но возможно, если покопаться в документации, где-то в недрах DDE есть тот самый app-user-data, в который можно поместить this, и который можно получить из какого-нить дескриптора, передающегося в колбек


--------------------
"Гений всегда разумнее, чем умнее. Ум — это машина, разум — водитель этой машины."
PM WWW ICQ   Вверх
500mhz
Дата 17.4.2012, 11:09 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


шайтан
***


Профиль
Группа: Завсегдатай
Сообщений: 1017
Регистрация: 5.5.2008
Где: Киев / Italy

Репутация: 3
Всего: 14



Цитата

thunk.m_mov = 0x042444C7; 
        thunk.m_this = (DWORD)pThis; 
        thunk.m_jmp = 0xe9; 

откуда берется jmp 0x042444C7  ?


--------------------

PM MAIL ICQ   Вверх
xvr
Дата 17.4.2012, 14:18 (ссылка) | (нет голосов) Загрузка ... Загрузка ... Быстрая цитата Цитата


Эксперт
****


Профиль
Группа: Комодератор
Сообщений: 7046
Регистрация: 28.8.2007
Где: Дублин, Ирландия

Репутация: 40
Всего: 223



Цитата(500mhz @  17.4.2012,  11:09 Найти цитируемый пост)
откуда берется jmp 0x042444C7  ? 

Это не jump. Это movl pThis,0x4(%esp). Jump это 0xE9 в поле m_jmp

PM MAIL   Вверх
  
Ответ в темуСоздание новой темы Создание опроса
Правила форума "C/C++: Системное программирование и WinAPI"
Fixin
GremlinProg
xvr
feodorv
  • Большое количество информации и примеров с использованием функций WinAPI можно найти в MSDN
  • Описание сообщений, уведомлений и примеров с использованием компонент WinAPI (BUTTON, EDIT, STATIC, и т.п.), можно найти в MSDN Control Library
  • Непосредственно, перед созданием новой темы, проверьте заголовок и удостоверьтесь, что он отражает суть обсуждения.
  • После заполнения поля "Название темы", обратите внимание на наличие и содержание панели "А здесь смотрели?", возможно Ваш вопрос уже был решен.
  • Приводите часть кода, в которой предположительно находится проблема или ошибка.
  • Если указываете код, пользуйтесь тегами [code][/code], или их кнопочными аналогами.
  • Если вопрос решен, воспользуйтесь соответствующей ссылкой, расположенной напротив названия темы.
  • Один топик - один вопрос!
  • Перед тем как создать тему - прочтите это .

На данный раздел распространяются Правила форума и Правила раздела С++:Общие вопросы .


Если Вам понравилась атмосфера форума, заходите к нам чаще! С уважением, Chipset, Step, Fixin, GremlinProg, xvr. feodorv.

 
0 Пользователей читают эту тему (0 Гостей и 0 Скрытых Пользователей)
0 Пользователей:
« Предыдущая тема | C/C++: Системное программирование и WinAPI | Следующая тема »


 




[ Время генерации скрипта: 0.0567 ]   [ Использовано запросов: 22 ]   [ GZIP включён ]


Реклама на сайте     Информационное спонсорство

 
По вопросам размещения рекламы пишите на vladimir(sobaka)vingrad.ru
Отказ от ответственности     Powered by Invision Power Board(R) 1.3 © 2003  IPS, Inc.