John wrote:
> Sorry, I must be really obtuse but I've walked through the code and I
> can't determine which property to read to get the "returned address"
> after Resolve() is called.
TPTRRecord.HostName contains the result of a qtPTR query. After Resolve()
returns, the QueryResult contains all of the individual results, as a single
query might return multiple records. Loop through the QueryResult checking
each TResultRecord.RecType and type-casting as needed, eg:
{code:delphi}
AIdDNSResolver.Resolve(IPAddress);
for I := 0 to AIdDNSResolver.QueryResult.Count-1 do
begin
case AIdDNSResolver.QueryResult[0].RecType of
qtPTR:
begin
HostName := TPTRRecord(AIdDNSResolver.QueryResult[0]).HostName;
if TextEndsWith(HostName, '.in-addr.arpa') then
begin
// call Resolve(HostName) with QueryType=qtPTR to get actual hostname...
// note: 74.125.224.72 resolves to nuq04s07-in-f8.1e100.net, not
google.com!
// if you were to call Resolve('google.com') with QueryType=qtA,
you get all
// of its IPs, but you might get different IPs depending on which DNS
// server you query...
end;
end;
...
end;
end;
{code}
> I've tried to figure out how to convert the TPTRRecord.RData into a
> TRDATARecord entry so I can get the IPAddress from that, but I can't
> figure out that offset either.
That will not work. TRDATARecord is used as the base class for TARecord,
which is only used for qtA queries. You cannot construct a TRDATARecord
from the TPTRRecord.RData property. They are different types of data. RData
merely contains the raw data of a given result. Each QueryType produces
a different kind of raw data, and each derived class parses its particular
raw data as it needs.
--
Remy Lebeau (TeamB)
|
Remy Lebeau (TeamB) wrote:
> note: 74.125.224.72 resolves to nuq04s07-in-f8.1e100.net, not
> google.com!
> if you were to call Resolve('google.com') with
> QueryType=qtA, you get all
> of its IPs, but you might get different IPs depending on
> which DNS server you query...
I guess I should try a different domain or I need to learn more on the
intricacies of DNS, because this is what happens when I tracert
google.com
Tracing route to google.com [74.125.224.71]
over a maximum of 30 hops:
.... (skipped first 2)
3 29 ms 10 ms 10 ms te-5-4-ur02.scotts.ca.sfba.comcast.net
[68.86.143.237]
4 18 ms 15 ms 15 ms
te-1-9-0-5-ar01.oakland.ca.sfba.comcast.net [68.87.226.210]
5 19 ms 22 ms 23 ms
he-2-14-0-0-cr01.sacramento.ca.ibone.comcast.net [68.86.90.137]
6 21 ms 19 ms 20 ms
pos-0-2-0-0-cr01.sanjose.ca.ibone.comcast.net [68.86.87.182]
7 18 ms 20 ms 17 ms
pos-0-7-0-0-pe01.529bryant.ca.ibone.comcast.net [68.86.88.202]
8 17 ms 16 ms 18 ms 66.208.228.226
9 18 ms 18 ms 17 ms 72.14.232.136
10 19 ms 19 ms 20 ms 64.233.174.19
11 17 ms 18 ms 18 ms nuq04s07-in-f7.1e100.net [74.125.224.71]
Trace complete.
So, how do I get to google.com with DNS resolution? Is there a better
one on this list?
http://compnetworking.about.com/od/dns_domainnamesystem/tp/top-free-internet-dns-servers.htm
--
John Kaster http://johnkaster.wordpress.com
http://transactis.com Seamless paper-free transactions
|
> {quote:title=John Kaster wrote:}{quote}
> I've got a friend who is a security specialist and he uses all kinds of
> tools OTHER than Delphi to write his utilities. I ask him why he's not
> using Delphi, when it should be able to do everything he's doing with
> all these various tools.
>
> ...
>
> --
> John Kaster http://johnkaster.wordpress.com
> http://transactis.com Seamless paper-free transactions
I don't know about that specific component but you can lookup IPv4 to hostname with the following:
{code}
unit ReverseLookup;
interface
type
TLookupCallback = procedure(Address, Hostname: string; Return: Integer);
procedure GetHostnameFromAddress(Address: string; Callback: TLookupCallback);
implementation
uses
Windows,
WinSock,
SysUtils;
const
NI_MAXHOST = 1025;
type
PAddrInfo = ^TAddrInfo;
TAddrInfo = record
ai_flags: Integer;
ai_family: Integer;
ai_socktype: Integer;
ai_protocol: Integer;
ai_addrlen: Integer;
ai_canonname: PAnsiChar;
ai_addr: PSockAddr;
ai_next: PAddrInfo;
end;
function getaddrinfo(pNodeName: PAnsiChar; pServiceName: PAnsiChar;
pHints: PAddrInfo; out ppResult: PAddrInfo): Integer; stdcall;
external 'Ws2_32.dll';
procedure freeaddrinfo(ai: PAddrInfo); stdcall; external 'Ws2_32.dll';
function getnameinfo(sa: PSockAddr; salen: Integer; host: PAnsiChar;
hostlen: DWORD; serv: PAnsiChar; servlen: DWORD; flags: Integer): Integer;
stdcall; external 'Ws2_32.dll';
procedure GetHostnameFromAddress(Address: string; Callback: TLookupCallback);
var
wsaData: TWSAData;
dwRetval: Integer;
ppResult: PAddrInfo;
ptr: PAddrInfo;
chostname: packed array [0..NI_MAXHOST-1] of AnsiChar;
Hostname: string;
begin
Hostname := '';
ppResult := nil;
FillChar(wsaData, SizeOf(TWSAData), #0);
dwRetval := WSAStartup(MAKEWORD(2, 2), wsaData);
if dwRetval = 0 then
begin
try
dwRetval := getaddrinfo(PAnsiChar(AnsiString(Address)), nil, nil,
ppResult);
if (dwRetval = 0) then
begin
try
ptr := ppResult;
while ptr <> nil do
begin
FillChar(chostname, SizeOf(chostname), #0);
case ptr^.ai_family of
AF_INET:
begin
dwRetval := getnameinfo(ptr^.ai_addr, SizeOf(TSockAddr),
@chostname[0], NI_MAXHOST, nil, 0, 0);
if dwRetval = 0 then
begin
Hostname := string(AnsiString(PAnsiChar(@chostname[0])));
Callback(Address, Hostname, 0);
end
else
begin
Callback(Address, '', dwRetval);
end;
end;
else
Callback(Address, '', -1);
end;
ptr := ptr^.ai_next;
end;
finally
freeaddrinfo(ppResult);
end;
end
else
begin
Callback(Address, '', dwRetval);
end;
finally
WSACleanup;
end;
end
else
begin
Callback(Address, '', dwRetval);
end;
end;
end.
{code}
Usage:
{code}
procedure Test;
procedure MyCallback(Address, Hostname: string; Return: Integer);
begin
case Return of
-1: WriteLn('Only IPv4 Address should be passed to GetHostnameFromAddress!');
0: WriteLn('Address: ', Address, ' -> Hostname: ', Hostname);
else
WriteLn('GetHostnameFromAddress failed with error: ', Return);
end;
end;
begin
GetHostnameFromAddress('173.194.67.94', @MyCallback);
GetHostnameFromAddress('74.125.224.72', @MyCallback);
end;
{code}
|