Создание зоны обновлений на UNIX сервере для Windows машин — различия между версиями

Материал из wiki.drweb.com
Перейти к: навигация, поиск
м
(Скрипт)
Строка 11: Строка 11:
 
  #!/usr/bin/perl -w
 
  #!/usr/bin/perl -w
 
  use Digest::MD5;
 
  use Digest::MD5;
  my $logdir = '/tmp/update';
+
  use LWP::UserAgent;
  my $basedir = '/tmp/500'; # папка, откуда обновляются виндовые агенты
+
use Compress::Zlib;
  my $drwebkey = '/tmp/drweb32-betatesting.key'; # путь к ключу drweb
+
use strict;
  # обновление баз и движков
+
  my $basedir = '/tmp/update/500'; # папка, откуда обновляются виндовые агенты
  system ('rm '. $logdir. '/*.*');
+
  my $drwebkey = '/home/axel/drweb32-betatesting.key'; # путь к ключу drweb
  system ('wget -P '.$logdir.' -r -l1 -nd -np http://msk3.drweb.com/pub/drweb/bases');
+
  my $tmpdir  = '/tmp'; # директория для временных файлов
  opendir (DIR, $logdir);
+
  my $url      = 'http://update.drweb.com/500/windows'; # одна из зон обновления Dr.Web
 +
 
 +
 +
# get MD5 hash of key-file
 +
open(FILE, $drwebkey) or die "Can't open '$drwebkey': $!";
 +
binmode(FILE);
 +
my $md5 =  Digest::MD5->new->addfile(*FILE)->hexdigest;
 +
 +
# download drweb32.lst
 +
download("$url/drweb32.lst",$basedir.'/drweb32.lst');
 +
 +
# parse drweb32.lst and download
 +
open LST, '<'."$basedir/drweb32.lst" or die "can't open $basedir/drweb32.lst ($!)\n";
 +
    while (<LST>) {
 +
            s/\r?\n$//; # remove \r\n, \n
 +
            /^\[[\w ]+\]$/ and next;
 +
            /^[-]/ and next; #skip delete;
 +
            my ( $filename, undef,$crc ) = /^[\+\=\@\!].*?([_a-zA-Z0-9\.\-]+)(\|.+)?[, \t]+([a-fA-F\d]+)?[, \t]*(\d+\.\d+)?/o
 +
                or print STDERR "unknown line \"$_\" in lst\n";
 +
            if (checkcrc32("$basedir/$filename",$crc) eq 0){
 +
            print "download $url/$filename, $crc\n"; #what try to download
 +
            my $ret unless download("$url/$filename","$basedir/$filename",$crc);
 +
            }
 +
            else  {
 +
                print "skip $url/$filename, $crc CRC is match\n"
 +
            }
 +
          }
 +
close LST;
 +
# solve problem with 403 Access not allowed for *today.vdb
 +
system ('wget -P '.$tmpdir.' -nd -np http://msk3.drweb.com/pub/drweb/bases/drwtoday.zip');
 +
  system ('wget -P '.$tmpdir.' -nd -np http://msk3.drweb.com/pub/drweb/bases/dwrtoday.zip');
 +
system ('wget -P '.$tmpdir.' -nd -np http://msk3.drweb.com/pub/drweb/bases/dwntoday.zip');
 +
  opendir (DIR, $tmpdir);
 
  my @files=readdir (DIR);
 
  my @files=readdir (DIR);
 
  closedir (DIR);
 
  closedir (DIR);
 
  foreach my $file (@files){
 
  foreach my $file (@files){
 
   if ($file =~ /zip/){
 
   if ($file =~ /zip/){
     system ('unzip -o '.$logdir.'/'.$file.' -d '.$basedir);
+
     system ('unzip -o '.$tmpdir.'/'.$file.' -d '.$basedir);
 
   }
 
   }
 
  }
 
  }
  # обновление компонентов
+
  sub checkcrc32 {
open(FILE, $drwebkey) or die "Can't open '$drwebkey': $!";
+
    my ($file,$crc)=@_;
binmode(FILE);
+
    my $crcf=0;
my $md5 = Digest::MD5->new->addfile(*FILE)->hexdigest;
+
    open FHC, '<'.$file or return 0;
my @components = qw(drweb32.lst
+
    $crcf=crc32($_,$crcf) while <FHC>;
                  update.drl
+
    return 0 if hex($crc) != $crcf;
                  drwebupw.exe
+
    close FHC;
                  dwshield.sys
+
    return 1;
                  spiderui.dll
+
                  drwebnet.sys
+
                  drwspcnt.dll
+
                  spider.cpl
+
                  drwspcnt.dll
+
                  dwprot.sys
+
                  dwprot.dll
+
                  dwengine.exe
+
                  dwinctl.dll
+
                  spideragent.exe
+
                  spideragent_set.exe
+
                  drweb32w.exe
+
                  drwebwcl.exe
+
                  spidergate.exe
+
                  spidergate_set.exe
+
                  spidernt.exe
+
                  spiderui.exe
+
                  spidercpl.exe
+
                  spider.sys
+
                  spiderml.exe
+
                  spml_set.exe
+
                  drwebsp.dll
+
                  drwreg.exe);
+
foreach my $component (@components) {
+
system ('wget -O '.$basedir.'/'.$component.
+
        ' -l 0'.
+
        ' --header="X-DrWeb-Validate:'.$md5.'"'.
+
        ' http://update.drweb.com/500/windows/'.$component);
+
 
  }
 
  }
  close (FILE);
+
  sub download {
opendir (C_DIR, $basedir);
+
    my ($url,$file,$crc)=@_;
  my @c_files=readdir (C_DIR);
+
    my $ua = LWP::UserAgent->new;
closedir (C_DIR);
+
    $ua->agent("DrWebUpdate-5.00.3.03020 (windows: 5.00.2195)");
  foreach my $c_file (@c_files){
+
    $ua->default_header('X-DrWeb-KeyNumber' => $md5);
     if ((-s $basedir.'/'.$c_file) eq 0){
+
   
        unlink ($basedir.'/'.$c_file)
+
    my $req = HTTP::Request->new(GET => $url);
 +
    my $res = $ua->request($req);
 +
   
 +
    if (! $res->is_success) {
 +
        print STDERR $res->status_line, " (file $url)\n";
 +
        return 0;
 +
    }
 +
     if ($crc and hex($crc) != crc32($res->content)) {
 +
        printf STDERR "file $url with frong crc: %X (expects $crc)\n",crc32($res->content);
 +
        return 0;
 
     }
 
     }
 +
    if ( ! open FH, '>'.$file) {
 +
        print STDERR "can't open $file ($!)\n";
 +
        return 0;
 +
    } 
 +
    print FH $res->content;
 +
    close FH;
 +
    return 1;
 
  }
 
  }
  

Версия 20:59, 8 апреля 2009

Attention.png

Внимание!
Корректность обновления компонентов антивируса, предложенная в данной статье не сильно высока, актуальность списка компонентов Вам придется поддерживать самостоятельно.

В статье рассмотрен способ создания зоны обновления антивируса Dr.Web на Linux для обновления windows-машин в локальной сети.

Замечание: данный способ не позволяет обновить базы родительского контроля. Feature request в баг-трекере:0025177

Введение

Антивирус Dr.Web обновляется при помощи программы DrWebUpW.exe, которая находится в каталоге %programfiles%\DrWeb. При запуске DrWebUpW читает последовательно файлы custom.drl и update.drl, лежащие с ним в одной папке. В этих файлах прописаны зоны обновления Dr.Web. Затем программа обновления скачивает с первой доступной зоны файл drweb32.lst, в котором хранятся хэши, расположение и команды установки всех файлов для обновления. Также необходимо знать, что существует ряд серверов, на которых Dr.Web выкладывает в свободном доступе антивирусные базы и движки, например, http://new-download.drweb.com/bases.

Скрипт

Скрипт, написанный на языке Perl, позволяет обновлять базы, движки и компоненты Dr.Web. Для обновления компонентов необходим действующий лицензионный ключевой файл от любого продукта Dr.Web. Компоненты, необходимые для обновления, можно указать в массиве @components

#!/usr/bin/perl -w
use Digest::MD5;
use LWP::UserAgent;
use Compress::Zlib;
use strict;
my $basedir  = '/tmp/update/500'; # папка, откуда обновляются виндовые агенты
my $drwebkey = '/home/axel/drweb32-betatesting.key'; # путь к ключу drweb
my $tmpdir   = '/tmp'; # директория для временных файлов 
my $url      = 'http://update.drweb.com/500/windows'; # одна из зон обновления Dr.Web
 

# get MD5 hash of key-file
open(FILE, $drwebkey) or die "Can't open '$drwebkey': $!";
binmode(FILE);
my $md5 =  Digest::MD5->new->addfile(*FILE)->hexdigest;

# download drweb32.lst
download("$url/drweb32.lst",$basedir.'/drweb32.lst'); 

# parse drweb32.lst and download
open LST, '<'."$basedir/drweb32.lst" or die "can't open $basedir/drweb32.lst ($!)\n";
    	 while (<LST>) {
            s/\r?\n$//; # remove \r\n, \n
            /^\[[\w ]+\]$/ and next;
            /^[-]/ and next; #skip delete;
            my ( $filename, undef,$crc ) = /^[\+\=\@\!].*?([_a-zA-Z0-9\.\-]+)(\|.+)?[, \t]+([a-fA-F\d]+)?[, \t]*(\d+\.\d+)?/o
               or print STDERR "unknown line \"$_\" in lst\n";
            if (checkcrc32("$basedir/$filename",$crc) eq 0){
            print "download $url/$filename, $crc\n"; #what try to download
            my $ret unless download("$url/$filename","$basedir/$filename",$crc);
            }
            else  {
                print "skip $url/$filename, $crc CRC is match\n"
            }
          }
close LST;
# solve problem with 403 Access not allowed for *today.vdb
system ('wget -P '.$tmpdir.' -nd -np http://msk3.drweb.com/pub/drweb/bases/drwtoday.zip');
system ('wget -P '.$tmpdir.' -nd -np http://msk3.drweb.com/pub/drweb/bases/dwrtoday.zip');
system ('wget -P '.$tmpdir.' -nd -np http://msk3.drweb.com/pub/drweb/bases/dwntoday.zip');
opendir (DIR, $tmpdir);
my @files=readdir (DIR);
closedir (DIR);
foreach my $file (@files){
 if ($file =~ /zip/){
   system ('unzip -o '.$tmpdir.'/'.$file.' -d '.$basedir);
 }
}
sub checkcrc32 {
    my ($file,$crc)=@_;
    my $crcf=0;
    open FHC, '<'.$file or return 0;
    $crcf=crc32($_,$crcf) while <FHC>;
    return 0 if hex($crc) != $crcf;
    close FHC;
    return 1;
}
sub download {
    my ($url,$file,$crc)=@_;
    my $ua = LWP::UserAgent->new;
    $ua->agent("DrWebUpdate-5.00.3.03020 (windows: 5.00.2195)");
    $ua->default_header('X-DrWeb-KeyNumber' => $md5);

    my $req = HTTP::Request->new(GET => $url);
    my $res = $ua->request($req);

    if (! $res->is_success) {
        print STDERR $res->status_line, " (file $url)\n";
        return 0;
    }
    if ($crc and hex($crc) != crc32($res->content)) {
        printf STDERR "file $url with frong crc: %X (expects $crc)\n",crc32($res->content);
        return 0;
    }
    if ( ! open FH, '>'.$file) {
        print STDERR "can't open $file ($!)\n";
        return 0;
    }  
    print FH $res->content;
    close FH;
    return 1;
}

Crontab

Теперь добавим задание в crontab, выполнив команду crontab -e:

# drweb update
0 */1 * * * /home/user/drwebupw.pl

Обновление windows-машин

DrWebUpW.exe /URL <UNC путь к папке $basedir>

Ссылки