Обновить
1
Павлов Максим@twr

Пользователь

1
Подписчики
Отправить сообщение
Собственно, Вы сами и подтвердили свои слова: «Котлеты отдельно, мухи отдельно». Хоть инспекторы с тестировщиками и решают одну и ту же проблему поиска дефектов, они всё-таки выискивают разные по типу дефекты. Следовательно, тут и подход разный, и инструменты, и люди с их квалификацией.
Забыл добавить, что стандарты не берутся с потолка и/или не являются чьей-то прихотью в стиле «Мне так нравится, я начальник, значит так и будет». Все стандарты в нашей компании выработаны ключевыми программистами, обсуждались всем коллективом, а потом уже внедрялись.
По пунктам:

>> А что это вы тут делаете?

Понимание инспектируемой задачи, бесспорно, важный момент. Но определение того, выполняет ли код поставленную задачу, это прерогатива отдела тестирования, а не инспектирования. Как Вы сами сказали, «Котлеты отдельно, мухи отдельно».

>> На вкус и цвет все фломастеры разные

Этого легко избежать, если инспектор будет руководствоваться чётко установленными стандартами. И при возврате кода программисту на доработку можно всегда указать на тот или иной пункт в Корпоративных Стандартах. У нас в компании таких документов несколько, в том числе и стандарты стилистического оформления кода.
Я смотрю, весь wasm здесь :)
Однако же, получать адрес процедуры в другом процессе начиная с систем, в которых активен ASLR, лучше как-то так (delphi 7):

function GetModuleHandleEx(sLibName: string; dwPID: DWORD): pointer;
var
  me: TMODULEENTRY32;
  hSnap: DWORD;
begin
result := nil;
hSnap := CreateToolhelp32Snapshot(TH32CS_SNAPMODULE, dwPID);
if hSnap <> DWORD(INVALID_HANDLE_VALUE) then
  begin
  me.dwSize := SizeOf(TMODULEENTRY32);
  if Module32First(hSnap, me) then
    repeat
      if UpperCase(string(me.szModule)) = UpperCase(sLibName) then
        begin
        result := pointer(me.modBaseAddr);
        break;
        end;
    until not Module32Next(hSnap, me);
  CloseHandle(hSnap);
  end;
end;

{$O-}
function GetProcAddressEx(sLibName, sFuncName: string; dwPID: DWORD): DWORD;
var
  hLib: DWORD;
begin
hLib := GetModuleHandle(PChar(sLibName));
result := DWORD(DWORD(GetProcAddress(hLib, PChar(sFuncName))) -
          hLib + DWORD(GetModuleHandleEx(sLibName, dwPID)));
end;
{$O+}
В подавляющем большинстве случаев, в рамках одной сессии, адреса загрузки системных библиотек будут совпадать. К примеру, сейчас, на рабочей Win7 sp0, адрес загрузки kernel32.dll одинаков во всех процессах. Однако, вчера, на компьютере жены с Win7 sp1, я наблюдал различие адресов загрузки user32.dll. Адреса было всего два и они никак не зависели от пользователя, под которым запущен процесс.
Глобальный хук тут не при чём. Alex имеет ввиду способ, при котором dll или кусок кода внедряется в АП целевого процесса (одного) и на него передаётся управление с помощью CreateRemoteThread().
Вынужден сильно поругать Ваш метод перехвата, хоть сама реализация и не является главной темой статьи.

1. Самый кошмар конечно в том, что происходит постоянная перезапись кода в контролируемых функциях. Вы задумывались что произойдёт, если какой-то параллельный поток в это же самое время будет выполнять код функции в затираемом месте?

2. Даже если от постоянной перезаписи избавиться, то остаётся ещё узкое место: однократная установка хука. По той же причине, описанной в предыдущем пункте, приложение может вылететь. Для того, чтобы решить данную проблему, Вы можете перечислять потоки и замораживать все, кроме своего, с помощью SuspendThread().

3. Правильная организация перехвата такова: Вы переносите несколько первых инструкций перехватываемой функции в заранее подготовленное место, после последней инструкции добавляете jmp на Ваш код-обработчик (получается эдакий переходник). В конце кода-обработчика jmp на первую незатёртую инструкцию оригинального кода. Ну и в начало перехватываемой функции лепите прыжок на «переходник». Это перехват до выполнения. Перехват после выполнения делается схожим образом, но там мы должны подменить адрес возврата на стеке в нашем «переходнике».

4. Нужно понимать, что не всякую функцию можно перехватить таким образом. К примеру, если перемещаемые инструкции будут содержать прыжки по относительным адресам, то после перемещения такой код перестанет быть рабочим. Благо, почти все WinAPI-функции содержат стандартный пролог в 5-6 байт, который можно смело двигать куда угодно.
Моя точка зрения такова, что если бы Маркони и Попов судились за своё [действительно супер-важное] изобретение так же, как судятся/«устраивают разборки» сейчас эти товарищи, то мы бы с Вами ныне не имели возможности так же свободно слушать радио, смотреть ТВ или коннектиться с ноутбука к своему чудесному Wi-Fi роутеру. Конкуренция должна быть здравой, «без фанатизма».
Так то оно так. Однако, всё уже давно «смешалось в доме Облонских». Там, где патентная система должна служить на благо общества, она служит дополнительным заработком как для крупных компаний-производителей, так и для, будь они неладны, «патентных троллей». Уж слишком свеж пример, где два гиганта судились из-за нескольких строк программного кода, который мог быть написан едва ли не каждым пятым студентом (подчёркиваю: написан в таком виде, чтобы вызвать подозрения в плагиате или, упаси всевышний, в тупом копипасте). Благо, судья оказался разумным.

Информация

В рейтинге
Не участвует
Откуда
Алматы (Алма-Ата), Алма-Атинская обл., Казахстан
Дата рождения
Зарегистрирован
Активность