print-dnsmasq.pl 5.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173
  1. #!/usr/bin/perl
  2. #
  3. # Copyright (C) Roman Dmitiriev, rnd@rajven.ru
  4. #
  5. use utf8;
  6. use open ":encoding(utf8)";
  7. use Encode;
  8. no warnings 'utf8';
  9. use English;
  10. use base;
  11. use FindBin '$Bin';
  12. use lib "/opt/Eye/scripts";
  13. use strict;
  14. use DBI;
  15. use Time::Local;
  16. use Net::Patricia;
  17. use NetAddr::IP;
  18. use Data::Dumper;
  19. use eyelib::config;
  20. use eyelib::main;
  21. use eyelib::database;
  22. use eyelib::net_utils;
  23. use File::Basename;
  24. use File::Path;
  25. use Fcntl qw(:flock);
  26. open(SELF,"<",$0) or die "Cannot open $0 - $!";
  27. flock(SELF, LOCK_EX|LOCK_NB) or exit 1;
  28. binmode(STDOUT,':utf8');
  29. setpriority(0,0,19);
  30. my %dhcp_conf;
  31. my $connected = new Net::Patricia;
  32. my $dhcp_networks = new Net::Patricia;
  33. my $int_addr=do_exec('/sbin/ip addr show | grep "scope global"');
  34. foreach my $address (split(/\n/,$int_addr)) {
  35. if ($address=~/inet\s+(.*)\s+brd/i) {
  36. if ($1) { $connected->add_string($1); }
  37. }
  38. }
  39. my %static_hole;
  40. my %mac_subnets;
  41. my @subnets=get_records_sql($dbh,'SELECT * FROM subnets WHERE dhcp=1 and office=1 and vpn=0 and hotspot=0 ORDER BY ip_int_start');
  42. foreach my $subnet (@subnets) {
  43. next if (!$subnet->{gateway});
  44. $dhcp_networks->add_string($subnet->{subnet});
  45. my $subnet_name = $subnet->{subnet};
  46. $subnet_name=~s/\/\d+$//g;
  47. $dhcp_conf{$subnet_name}->{first_ip}=IpToStr($subnet->{dhcp_start});
  48. $dhcp_conf{$subnet_name}->{last_ip}=IpToStr($subnet->{dhcp_stop});
  49. $dhcp_conf{$subnet_name}->{relay_ip}=IpToStr($subnet->{gateway});
  50. my $dhcp=GetDhcpRange($subnet->{subnet});
  51. if ($subnet->{static}) {
  52. $static_hole{$dhcp_conf{$subnet_name}->{last_ip}}->{mac}="01:02:03:04:05:06";
  53. $static_hole{$dhcp_conf{$subnet_name}->{last_ip}}->{skip}=0;
  54. print "dhcp-range=net-$subnet_name,$dhcp_conf{$subnet_name}->{last_ip},$dhcp_conf{$subnet_name}->{last_ip},$dhcp->{mask},$subnet->{dhcp_lease_time}m\n";
  55. } else {
  56. print "dhcp-range=net-$subnet_name,$dhcp_conf{$subnet_name}->{first_ip},$dhcp_conf{$subnet_name}->{last_ip},$dhcp->{mask},$subnet->{dhcp_lease_time}m\n";
  57. }
  58. print "dhcp-option=net:net-$subnet_name,option:router,$dhcp_conf{$subnet_name}->{relay_ip}\n";
  59. }
  60. #get userid list
  61. my $sSQL="SELECT id,ip,ip_int,mac,comments,dns_name,dhcp_option_set,dhcp_acl,ou_id FROM User_auth where dhcp=1 and deleted=0 ORDER by ip_int";
  62. my @users = get_records_sql($dbh,$sSQL);
  63. foreach my $row (@users) {
  64. next if (!$row);
  65. next if (!$dhcp_networks->match_string($row->{ip}));
  66. next if (!$row->{mac});
  67. next if (!$row->{ip});
  68. next if (is_default_ou($dbh,$row->{ou_id}));
  69. if (exists $static_hole{$row->{ip}}) { $static_hole{$row->{ip}}{skip}=1; }
  70. print '#Comment:'.$row->{comments}."\n" if ($row->{comments});
  71. my $dns_name = '';
  72. if ($row->{dns_name}) {
  73. print '#DNS:'.$row->{dns_name}."\n";
  74. $dns_name = ','.$row->{dns_name};
  75. }
  76. my $dhcp_set = '';
  77. if ($row->{dhcp_option_set}) {
  78. $dhcp_set = ',set:'.$row->{dhcp_option_set};
  79. }
  80. print 'dhcp-host='.$row->{mac}.$dns_name.','.$row->{ip}.$dhcp_set."\n";
  81. }
  82. foreach my $ip (keys %static_hole) {
  83. if (!$static_hole{$ip}{skip}) {
  84. print '#BlackHole for static subnet\n';
  85. print 'dhcp-host='.$static_hole{$ip}->{mac}.', '.$ip."\n";
  86. }
  87. }
  88. # DNS
  89. print "#--- DNS ---#\n";
  90. #get userid list
  91. my $sSQL="SELECT id,ou_id,ip,dns_name,dhcp_hostname,dns_ptr_only FROM User_auth WHERE deleted=0 AND ip>'' AND (dns_name>'' OR dhcp_hostname>'') AND dns_name NOT LIKE '%.' ORDER by ip_int;";
  92. my @users = get_records_sql($dbh,$sSQL);
  93. foreach my $row (@users) {
  94. next if (!$row);
  95. next if (is_default_ou($dbh,$row->{ou_id}));
  96. next if (!$office_networks->match_string($row->{ip}));
  97. my $dns_name = trim($row->{dns_name});
  98. if ($dns_name) {
  99. $dns_name =~s/_/-/g;
  100. # $dns_name =~s/[\.]/-/g;
  101. $dns_name =~s/ /-/g;
  102. $dns_name =~s/-$//g;
  103. $dns_name = trim($dns_name);
  104. if ($dns_name and $dns_name!~/\.$domain_name$/) { $dns_name = $dns_name .".".$domain_name; }
  105. } else { $dns_name=''; }
  106. next if (!$dns_name);
  107. #if (!$row->{dns_ptr_only} and ($dns_name or $row->{dhcp_hostname})) {
  108. if (!$row->{dns_ptr_only} and $dns_name) {
  109. print '#Comment:'.$row->{comments}."\n" if ($row->{comments});
  110. if ($dns_name) {
  111. print '#DNS A-record '.$dns_name."\n";
  112. print 'address=/'.$dns_name.'/'.$row->{ip}."\n";
  113. }
  114. # else {
  115. # if ($row->{dhcp_hostname} and $row->{dhcp_hostname}!~/UNDEFINED/i) {
  116. # $dns_name = $row->{dhcp_hostname};
  117. # $dns_name = $dns_name .".".$domain_name; }
  118. # $dns_name =~s/_/-/g;
  119. ## $dns_name =~s/[\.]/-/g;
  120. # $dns_name =~s/ /-/g;
  121. # $dns_name =~s/-$//g;
  122. # $dns_name = trim($dns_name);
  123. # if ($dns_name) {
  124. # print '#DNS-from-DHCP A-record '.$dns_name."\n";
  125. # print 'address=/'.$dns_name.'/'.$row->{ip}."\n";
  126. # }
  127. # }
  128. #aliases
  129. if ($dns_name) {
  130. my $aSQL="SELECT * FROM `User_auth_alias` WHERE auth_id=$row->{id} AND alias>'' AND alias NOT LIKE '%.';";
  131. my @aliases = get_records_sql($dbh,$aSQL);
  132. print '#DNS aliases for '.$dns_name."\n" if (@aliases and scalar @aliases);
  133. foreach my $alias (@aliases) {
  134. my $dns_alias = trim($alias->{alias});
  135. # $dns_alias =~s/$domain_name//i;
  136. $dns_alias =~s/_/-/g;
  137. $dns_alias =~s/[\.]/-/g;
  138. $dns_alias =~s/ /-/g;
  139. $dns_alias =~s/-$//g;
  140. $dns_alias = trim($dns_alias);
  141. if ($dns_alias and $dns_alias !~ /\.\Q$domain_name\E$/i) { $dns_alias = $dns_alias .".".$domain_name; }
  142. print "cname=".$dns_alias.",".$dns_name."\n" if ($dns_alias);
  143. }
  144. }
  145. }
  146. my $ptr_record='';
  147. if ($dns_name and $row->{ip}=~/([0-9]{1,3})\.([0-9]{1,3})\.([0-9]{1,3})\.([0-9]{1,3})/) {
  148. $ptr_record=$4.".".$3.".".$2.".".$1.".in-addr.arpa";
  149. print '#PTR for '.$dns_name."\n";
  150. print 'ptr-record='.$ptr_record.','.$dns_name."\n";
  151. }
  152. }
  153. exit 0;