オープンリゾルバ撲滅に向けて
イタズラしたい人はご遠慮ください。作り方を公開しておきます。
※ Nginx + Mojolicious の環境を前提としています。
apacheでも大丈夫です♪
■Mojoliciousの環境作成
apt-get install perlbrew perlbrew init perlbrew install perl-5.16.3 perlbrew install-cpanm cat ~/perl5/perlbrew/etc/bashrc >> ~/.bashrc sourc ~/.bashrc perlbrew use perl-5.16.3 cpanm install Mojolicious cpanm install Net::DNS cpanm install IO::Socket::IP
■プログラム
vi myapp.pl ----- #!/usr/bin/env perl use Mojolicious::Lite; use Net::DNS; use Sys::Syslog; use IO::Socket::IP; # share our %h_checkedFlag; # Documentation browser under "/perldoc" plugin 'PODRenderer'; openlog("dnschk", 'ndelay,pid', 'user'); my $res = Net::DNS::Resolver->new; $res->udp_timeout(1); $res->tcp_timeout(1); get '/check' =>sub { my $c = shift; my $flag = 0; #my $rAddr = $c->tx->remote_address; my $rAddr = $c->req->headers->header('X-Forwarded-For'); # When the IP is same, stop 60 sec. if(time - $h_checkedFlag{$rAddr} < 60 ){$flag = 3;} $h_checkedFlag{$rAddr} = time; if($rAddr =~ /[^.:0-9a-fA-F]+/) { $flag = 2; $rAddr = ''; } elsif(!$flag) { foreach my $vc (0..1) { $res->usevc($vc); $res->nameservers($rAddr); my $reply = $res->search("m.ROOT-SERVERS.NET"); if ($reply) { foreach my $rr ($reply->answer) { next unless $rr->type eq "A"; my $addr = $rr->address; $flag = 1; syslog('info', '%s,%s', $rAddr, $addr); } } else { syslog('info', 'query failed %s', $rAddr); } } } my $data = { ip => $rAddr, flag => $flag }; $c->render(json => $data); }; closelog; app->start; -----
プログラムを起動する
morbo myapp.pl
■index.html
cd /var/www/vhost/dnschk.snowdrop.asia/ wget 'http://code.jquery.com/jquery-1.11.1.min.js' vi index.html ------------
■nginxの設定
vi /etc/nginx/conf.d/dnschk.snowdrop.asia.conf ----- proxy_set_header Host $host; proxy_set_header X-Real-IP $remote_addr; proxy_set_header X-Remote-Addr $remote_addr; proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; location /check { proxy_pass http://127.0.0.1:3000/check; } -----
反映する
sudo /etc/init.d/nginx reload