На главную Наши проекты:
Журнал   ·   Discuz!ML   ·   Wiki   ·   DRKB   ·   Помощь проекту
ПРАВИЛА FAQ Помощь Участники Календарь Избранное RSS
msm.ru
! Перед отправкой сообщения внимательно прочтите правила раздела!!!
1. Запрещается обсуждать написание вирусов, троянов и других вредоносных программ!
2. Помните, что у нас есть FAQ раздела Assembler и Полезные ссылки. Посмотрите, возможно, там уже имеется решение вашего вопроса.

3. Настоятельно рекомендуем обратить особое внимание на правила форума, которые нарушаются чаще всего:
  3.1. Заголовок темы должен кратко отражать её суть. Темы с заголовками типа "Срочно помогите!" или "Ассемблер" будут отправляться в Корзину для мусора.
  3.2. Исходники программ обязательно выделяйте тегами [code]...[/code] (одиночные инструкции можно не выделять).
  3.3. Нежелательно поднимать старые темы (не обновлявшиеся более года) без веской на то причины.

Не забывайте также про главные Правила форума!

Добро пожаловать и приятного вам общения!!! ;)
 
Модераторы: Jin X, Qraizer
  
> __fastcall -> cdecl , Как правильно сделать переход?
    Добрый день.

    Подскажите как правильно сделать переход из соглашения __fastcall в соглашение cdecl?
    Я хукаю __fastcall функцию и вызываю в хуке свою функцию cdecl. Делал так: резервировал буфер в целевом процессе, и в этот буфер записывал состояние регистров
    ExpandedWrap disabled
      MOV [ADR], ESI
      MOV [ADR], EAX
      MOV [ADR], ECX
      MOV [ADR], EDX
      MOV [ADR], EBX
      тут вызываю свою функцию cdecl и восстанавливаю регистры
      MOV ESI, [ADR]
      MOV EAX, [ADR]
      MOV ECX, [ADR]
      MOV EDX, [ADR]
      MOV EBX, [ADR]
      потом делаю PUSH ESI, чтоб вернуть адрес возврата в стек


    Все это шаманство работало до поры, но сейчас спотыкается. Уверен, что все это жуткий костыль, и вобще так делать нельзя.
    Подскажите пожалуйста как правильно сделать переходник? Чтобы после работы моей функции стек и регистры вернулись "как и было"?
      Никакого стандарта на соглашение __fastcall не существует. Каждый компилятор может трактовать его по-разному. Посему нет и определённых правил преобразования __fastcall во что-то иное, кроме тех, которые известны самому компилятору, выполнившему этот самый __fastcall. Если это соглашение описано в документации на компилятор, то следует изучить материал, и написать соответствующий переходник будет несложно. Но проще просто изначально отказаться от __fastcall. В противном случае шаманства, работающего на честном слове, не избежать.
        Спасибо разъяснил про фасткал. А если я например знаю, как передаются параметры? Есть же какие то общие принципы таких переходников, и в них врят-ли делали так же как я (сохраняли регистры в буфер)?
        С вызовом моей функции на cdecl проблем нет - cdecl берет все из стека, загнать нужное туда не проблема. Проблема после ее работы восстановить регистры и стек в изначальное состояние...
          Цитата Rzonex @
          Проблема после ее работы восстановить регистры и стек в изначальное состояние...
          Ну а я-то об чём. Не зная соглашений целевого компилятора, ты ничего надёжного не сделаешь. Вот с чего ты взял, что сохранения регистров достаточно? Или даже, что сохранение регистров ничего не поломает? А вдруг компилятор через какой-нибудь EBP передаёт и возвращает ссылку на какие-то дополнительные стековые фреймы?
            Жаль :( Можно еще вопрос - как из стека верхнюю запись удалить? Можно засрать регистр сделав pop ESI например. А можно не засирая регистры ее удалить совсем?
              Цитата Rzonex @
              как из стека верхнюю запись удалить?

              ExpandedWrap disabled
                add  esp,4         ; удалить один аргумент
                sub  esp,4         ; зарезервировать dword в стеке
              Сообщение отредактировано: core-i7 -
              0 пользователей читают эту тему (0 гостей и 0 скрытых пользователей)
              0 пользователей:


              Рейтинг@Mail.ru
              [ Script execution time: 0,0315 ]   [ 15 queries used ]   [ Generated: 28.03.24, 14:07 GMT ]