/[lcore]/trunk/dnssync.pas
ViewVC logotype

Diff of /trunk/dnssync.pas

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

revision 2 by beware, Sun Mar 30 00:16:07 2008 UTC revision 20 by beware, Fri Dec 26 19:17:00 2008 UTC
# Line 25  Line 25 
25        sockets,        sockets,
26        fd_utils,        fd_utils,
27      {$endif}      {$endif}
28        lcorernd,
29      sysutils;      sysutils;
30    
31  //convert a name to an IP  //convert a name to an IP
# Line 44  Line 45 
45  //details as above  //details as above
46  function reverselookup(ip:tbinip;timeout:integer):string;  function reverselookup(ip:tbinip;timeout:integer):string;
47    
 {$ifdef linux}{$ifdef ipv6}  
 function getv6localips:tbiniplist;  
 procedure initpreferredmode;  
48    
 var  
   preferredmodeinited:boolean;  
   
 {$endif}{$endif}  
49    
50  const  const
51    tswrap=$4000;    tswrap=$4000;
# Line 61  Line 55 
55    defaulttimeout=10000;    defaulttimeout=10000;
56    const mintimeout=16;    const mintimeout=16;
57    
58      toport='53';
59    
60  var  var
   dnssyncserver:string;  
61    id:integer;    id:integer;
62    
63    sendquerytime:array[0..numsock-1] of integer;    sendquerytime:array[0..numsock-1] of integer;
# Line 84  Line 79 
79    numsockused:integer;    numsockused:integer;
80    fd:array[0..numsock-1] of integer;    fd:array[0..numsock-1] of integer;
81    state:array[0..numsock-1] of tdnsstate;    state:array[0..numsock-1] of tdnsstate;
82      toaddr:array[0..numsock-1] of tbinip;
83    
84  {$ifdef syncdnscore}  {$ifdef syncdnscore}
85    
# Line 122  Line 118 
118    result := false;    result := false;
119    if len = 0 then exit; {no packet}    if len = 0 then exit; {no packet}
120    
121    if dnssyncserver <> '' then addr := dnssyncserver else addr := getcurrentsystemnameserver(id);    if overridednsserver <> '' then addr := overridednsserver else addr := getcurrentsystemnameserver(id);
122    port := '53';  
123      {$ifdef ipv6}{$ifdef win32}
124      if toaddr[socknum].family = AF_INET6 then if (useaf = 0) then useaf := useaf_preferv6;
125      {$endif}{$endif}
126    
127    makeinaddrv(ipstrtobinf(addr),port,inaddr);    port := toport;
128      toaddr[socknum] := ipstrtobinf(addr);
129      makeinaddrv(toaddr[socknum],port,inaddr);
130    
131    sendto(fd[socknum],packet,len,0,inaddr,inaddrsize(inaddr));    sendto(fd[socknum],packet,len,0,inaddr,inaddrsize(inaddr));
132    sendquerytime[socknum] := getts;    sendquerytime[socknum] := getts;
# Line 142  Line 143 
143    //init both sockets smultaneously, always, so they get succesive fd's    //init both sockets smultaneously, always, so they get succesive fd's
144    if fd[0] > 0 then exit;    if fd[0] > 0 then exit;
145    
146    if dnssyncserver <> '' then addr := dnssyncserver else addr := getcurrentsystemnameserver(id);    if overridednsserver <> '' then addr := overridednsserver else addr := getcurrentsystemnameserver(id);
147    //must get the DNS server here so we know to init v4 or v6    //must get the DNS server here so we know to init v4 or v6
148    
   fillchar(inaddrtemp,sizeof(inaddrtemp),0);  
149    ipstrtobin(addr,biniptemp);    ipstrtobin(addr,biniptemp);
   if biniptemp.family = 0 then biniptemp.family := AF_INET;  
150    
151    inaddrtemp.inaddr.family := biniptemp.family;    if biniptemp.family = AF_INET6 then biniptemp := ipstrtobinf('::') else biniptemp := ipstrtobinf('0.0.0.0');
152    
153    
154    for a := 0 to numsockused-1 do begin    for a := 0 to numsockused-1 do begin
155        makeinaddrv(biniptemp,inttostr( 1024 + randominteger(65536 - 1024) ),inaddrtemp);
156    
157      fd[a] := Socket(biniptemp.family,SOCK_DGRAM,0);      fd[a] := Socket(biniptemp.family,SOCK_DGRAM,0);
158    
159      If {$ifndef win32}Not{$endif} Bind(fd[a],inAddrtemp,inaddrsize(inaddrtemp)) Then begin      If {$ifndef win32}Not{$endif} Bind(fd[a],inAddrtemp,inaddrsize(inaddrtemp)) Then begin
# Line 182  Line 184 
184    finished:array[0..numsock-1] of boolean;    finished:array[0..numsock-1] of boolean;
185    a,b:integer;    a,b:integer;
186    
187      Src    : TInetSockAddrV;
188      Srcx   : {$ifdef win32}sockaddr_in{$else}TInetSockAddrV{$endif} absolute Src;
189      SrcLen : Integer;
190      fromip:tbinip;
191      fromport:string;
192    
193  begin  begin
194    if timeout < mintimeout then timeout := defaulttimeout;    if timeout < mintimeout then timeout := defaulttimeout;
195    
# Line 249  Line 257 
257          fillchar(state[socknum].recvpacket,sizeof(state[socknum].recvpacket),0);          fillchar(state[socknum].recvpacket,sizeof(state[socknum].recvpacket),0);
258          msectotimeval(lag,(currenttime-sendquerytime[socknum]) and tsmask);          msectotimeval(lag,(currenttime-sendquerytime[socknum]) and tsmask);
259    
260          if dnssyncserver = '' then reportlag(id,(lag.tv_sec*1000000)+lag.tv_usec);          if overridednsserver = '' then reportlag(id,(lag.tv_sec*1000000)+lag.tv_usec);
261          state[socknum].recvpacketlen := recv(fd[socknum],state[socknum].recvpacket, SizeOf(state[socknum].recvpacket),0);  
262            SrcLen := SizeOf(Src);
263            state[socknum].recvpacketlen := recvfrom(fd[socknum],state[socknum].recvpacket, SizeOf(state[socknum].recvpacket),0,Srcx,SrcLen);
264    
265            if (state[socknum].recvpacketlen > 0) then begin
266              fromip := inaddrvtobinip(Src);
267              fromport := inttostr(htons(src.InAddr.port));
268              if ((not comparebinip(toaddr[socknum],fromip)) or (fromport <> toport)) then begin
269    //            writeln('dnssync received from wrong IP:port ',ipbintostr(fromip),'#',fromport);
270                state[socknum].recvpacketlen := 0;
271              end else begin
272          state[socknum].parsepacket := true;          state[socknum].parsepacket := true;
273          needprocessing[socknum] := true;          needprocessing[socknum] := true;
274        end;        end;
275      end;      end;
276          end;
277        end;
278      if selectresult < 0 then exit;      if selectresult < 0 then exit;
279      if selectresult = 0 then begin      if selectresult = 0 then begin
280    
281        currenttime := getts;        currenttime := getts;
282    
283        if dnssyncserver = '' then reportlag(id,-1);        if overridednsserver = '' then reportlag(id,-1);
284        if (currenttime >= endtime) and ((not wrapmode) or (currenttime < starttime)) then begin        if (currenttime >= endtime) and ((not wrapmode) or (currenttime < starttime)) then begin
285          exit;          exit;
286        end else begin        end else begin
# Line 274  Line 294 
294  end;  end;
295  {$endif}  {$endif}
296    
 procedure addipsoffamily(var l:tbiniplist;const l2:tbiniplist;family:integer);  
 var  
   a:integer;  
   biniptemp:tbinip;  
 begin  
   for a := biniplist_getcount(l2)-1 downto 0 do begin  
     biniptemp := biniplist_get(l2,a);  
     if (biniptemp.family = family) then biniplist_add(l,biniptemp);  
   end;  
 end;  
297    
298    
299  function forwardlookuplist(name:string;timeout:integer):tbiniplist;  function forwardlookuplist(name:string;timeout:integer):tbiniplist;
# Line 324  Line 334 
334    {$endif}    {$endif}
335    begin    begin
336    {$ifdef syncdnscore}    {$ifdef syncdnscore}
337      {$ifdef linux}{$ifdef ipv6}initpreferredmode;{$endif}{$endif}      {$ifdef ipv6}initpreferredmode;{$endif}
338    
339      numsockused := 0;      numsockused := 0;
340    
# Line 383  Line 393 
393    {$endif}    {$endif}
394  end;  end;
395    
 {$ifdef linux}{$ifdef ipv6}{$ifdef syncdnscore}  
 function getv6localips:tbiniplist;  
 var  
   t:textfile;  
   s,s2:string;  
   ip:tbinip;  
   a:integer;  
 begin  
   result := biniplist_new;  
   
   assignfile(t,'/proc/net/if_inet6');  
   {$i-}reset(t);{$i+}  
   if ioresult <> 0 then exit; {none found, return empty list}  
   
   while not eof(t) do begin  
     readln(t,s);  
     s2 := '';  
     for a := 0 to 7 do begin  
       if (s2 <> '') then s2 := s2 + ':';  
       s2 := s2 + copy(s,(a shl 2)+1,4);  
     end;  
     ipstrtobin(s2,ip);  
     if ip.family <> 0 then biniplist_add(result,ip);  
   end;  
   closefile(t);  
 end;  
   
 procedure initpreferredmode;  
 var  
   l:tbiniplist;  
   a:integer;  
   ip:tbinip;  
   ipmask_global,ipmask_6to4,ipmask_teredo:tbinip;  
   
 begin  
   if preferredmodeinited then exit;  
   if useaf <> useaf_default then exit;  
   useaf := useaf_preferv4;  
   l := getv6localips;  
   ipstrtobin('2000::',ipmask_global);  
   ipstrtobin('2001::',ipmask_teredo);  
   ipstrtobin('2002::',ipmask_6to4);  
   {if there is any v6 IP which is globally routable and not 6to4 and not teredo, prefer v6}  
   for a := biniplist_getcount(l)-1 downto 0 do begin  
     ip := biniplist_get(l,a);  
     if not comparebinipmask(ip,ipmask_global,3) then continue;  
     if comparebinipmask(ip,ipmask_teredo,32) then continue;  
     if comparebinipmask(ip,ipmask_6to4,16) then continue;  
     useaf := useaf_preferv6;  
     preferredmodeinited := true;  
     exit;  
   end;  
 end;  
   
 {$endif}{$endif}{$endif}  
   
396  {$ifdef win32}  {$ifdef win32}
397    var    var
398      wsadata : twsadata;      wsadata : twsadata;

Legend:
Removed from v.2  
changed lines
  Added in v.20

No admin address has been configured">No admin address has been configured
ViewVC Help
Powered by ViewVC 1.1.26