Rilevare IP (Delphi XE)

di il
13 risposte

Rilevare IP (Delphi XE)

Per conoscere l'IP assegnato in rete usavo questo codice che giravo sotto Delphi 7:
function getIPs: Tstrings;
type
  TaPInAddr = array[0..10] of PInAddr;
  PaPInAddr = ^TaPInAddr;
var
  phe: PHostEnt;
  pptr: PaPInAddr;
  Buffer: array[0..63] of Char;
  I: Integer;
  GInitData: TWSAData;
begin
  WSAStartup($101, GInitData);
  Result := TstringList.Create;
  Result.Clear;
  GetHostName(Buffer, SizeOf(Buffer));
  phe := GetHostByName(buffer);
  if phe = nil then Exit;
  pPtr := PaPInAddr(phe^.h_addr_list);
  I    := 0;
  while pPtr^[I] <> nil do
  begin
    Result.Add(inet_ntoa(pptr^[I]^));
    Inc(I);
  end;
  WSACleanup;
end;
adesso che uso Delphi XE mi da questo errore:
[DCC Error] ip_mio.pas(41): E2010 Incompatible types: 'PAnsiChar' and 'array[0..63] of Char'

13 Risposte

  • Re: Rilevare IP (Delphi XE)

    MrCamarium ha scritto:


    Per conoscere l'IP assegnato in rete usavo questo codice che giravo sotto Delphi 7 [...]
    adesso che uso Delphi XE mi da questo errore:
    [DCC Error] ip_mio.pas(41): E2010 Incompatible types: 'PAnsiChar' and 'array[0..63] of Char'
    A partire da Delphi 2009, le stringhe non sono più ANSI bensì Unicode!

    Ne consegue che nell'invocazione di determinate API sarebbe meglio utilizzarne la versione compatibile con questo standard, mentre per le API che utilizzano ancora lo standard di decodifica ANSI, occorre usare il tipo giusto di stringhe e di caratteri.

    Se vuoi approfondire l'argomento, c'è un white paper che spiega tutto ciò che va conosciuto.

    Nel caso in esame qui, credo basti dichiarare l'array così:
    array[0..63] of AnsiChar


    Ciao!
  • Re: Rilevare IP (Delphi XE)

    Grazie sei sempre molto gentile!
    Ho fatto la dovuta modifica ma mi da un errore di incompatibilità a questa riga:
    while pPtr^[I] <> nil do
    l'errore è:
    [DCC Error] ip_mio.pas(46): E2008 Incompatible types
  • Re: Rilevare IP (Delphi XE)

    Se non ricordo male la libreria Indy ha già qualcosa che con il minimo sforzo riesce a darti IP del client dove lavori, in questo modo ti liberi dalle varie API e lasci il lavoro sporco alla libreria.
    Nick.
  • Re: Rilevare IP (Delphi XE)

    Se sei in una rete, tipo a casa dietro un router, credo che si riesca a vedere solo l'IP locale però.
  • Re: Rilevare IP (Delphi XE)

    Nicola ha scritto:


    Se non ricordo male la libreria Indy ha già qualcosa che con il minimo sforzo riesce a darti IP del client dove lavori, in questo modo ti liberi dalle varie API e lasci il lavoro sporco alla libreria.
    Nick.
    Si è vero con questo codice.
    procedure TForm1.FormCreate(Sender: TObject);
    var
      ids: TidIpWatch;
    begin
     ids := TidIpWatch.Create;
     Label2.Caption := 'IP:' + ids.LocalIP;
     ids.Free;
    end;
    Ma come dicevi tu da solo l'IP locale.
  • Re: Rilevare IP (Delphi XE)

    Cercherò un'altra soluzione per avere L'IP pubblico ma mi piacerebbe far funzionare questo codice:
    function getIPs: Tstrings;
    type
      TaPInAddr = array[0..63] of AnsiChar;
      PaPInAddr = ^TaPInAddr;
    var
      phe: PHostEnt;
      pptr: PaPInAddr;
      Buffer: array[0..63] of AnsiChar;
      I: Integer;
      GInitData: TWSAData;
    begin
      WSAStartup($101, GInitData);
      Result := TstringList.Create;
      Result.Clear;
      GetHostName(Buffer, SizeOf(Buffer));
      phe := GetHostByName(buffer);
      if phe = nil then Exit;
      pPtr := PaPInAddr(phe^.h_addr_list);
      I    := 0;
      while pPtr^[I] <> nil do
      begin
        Result.Add(inet_ntoa(pptr^[I]^));
        Inc(I);
      end;
      WSACleanup;
    end;
    Al momento mi da questo errore:
    [DCC Error] ip_mio.pas(46): E2008 Incompatible types
  • Re: Rilevare IP (Delphi XE)

    MrCamarium ha scritto:


    Al momento mi da questo errore:
    [DCC Error] ip_mio.pas(46): E2008 Incompatible types
    Hai provato a verificare di che tipo sono quelle variabili?
    Hai provato a cercare documentazione su ciò che fa la funzione e quali parametri si aspetta?
    Hai provato a capire quello che fa il codice in quel frangente e a cosa servono le istruzioni?

    Alzare le mani a ogni errore senza approfondire un minimo vuole dire di fatto delegare ad altri l'analisi del problema, le ricerche annesse e connesse, la formulazione di una soluzione.

    Siamo qui a dare una mano, non a fare consulenza.
  • Re: Rilevare IP (Delphi XE)

    MrCamarium ha scritto:


    
    function getIPs: Tstrings;
    type
      TaPInAddr = array[0..63] of AnsiChar;
      PaPInAddr = ^TaPInAddr;
    var
      phe: PHostEnt;
      pptr: PaPInAddr;
      Buffer: array[0..63] of AnsiChar;
      I: Integer;
      GInitData: TWSAData;
    begin
      WSAStartup($101, GInitData);
      Result := TstringList.Create;
      Result.Clear;
      GetHostName(Buffer, SizeOf(Buffer));
      phe := GetHostByName(buffer);
      if phe = nil then Exit;
      pPtr := PaPInAddr(phe^.h_addr_list);
      I    := 0;
      while pPtr^[I] <> nil do
      begin
        Result.Add(inet_ntoa(pptr^[I]^));
        Inc(I);
      end;
      WSACleanup;
    end;
    Al momento mi da questo errore:
    [DCC Error] ip_mio.pas(46): E2008 Incompatible types
    Così ad occhio l'errore è all'inizio del ciclo While, dove cerchi di ciclare dentro un puntatore di un puntatore ad un array di char, dunque il "Nil" non va bene, un "Null" dovrebbe risolvere il tuo errore, ma questo è solo l'inizio, credo che quel quadruplo puntatore nel result.add ti farà impazzire ... e non poco.... cmq la soluzione è cambiare la dichiarazione in pptr: TInAddr, poi io personalmente cambierei anche buffer da 63 a 255.

    PS: Spero di non aver scritto qualche cavolata, appena ho tempo accendo il pc e provo....
    Un saluto
    Nick
  • Re: Rilevare IP (Delphi XE)

    Grazie del tuo intervento. Apportando le modifiche da te suggerite sulla riga:
    Result.Add(inet_ntoa(pptr^[I]^));
    mi da questo errore:
    [DCC Error] ip_mio.pas(48): E2017 Pointer type required
  • Re: Rilevare IP (Delphi XE)

    Io uso questa per l'IP della macchina, per quello esterno devi interrogare un sito che ti restituisce il tuo indirizzo verso l'esterno:
     Function GetIPAddress : String;
         type pu_long     = ^u_long;
          var varTWSAData : TWSAData;
              varPHostEnt : PHostEnt;
              varTInAddr  : TInAddr;
              namebuf     : Array[0..255] of ansichar;
        begin
              If WSAStartup($101,varTWSAData) <> 0
                 Then Begin
                      Result := '';
                      End
                 Else Begin
                      gethostname(namebuf,sizeof(namebuf));
                      varPHostEnt := gethostbyname(namebuf);
                      varTInAddr.S_addr := u_long(pu_long(varPHostEnt^.h_addr_list^)^);
                      Result := inet_ntoa(varTInAddr);
                      End;
              WSACleanup;
        end;
  • Re: Rilevare IP (Delphi XE)

    Perfetto grazie, rispetto al codice che avevo questo è più semplice e funzionale.
  • Re: Rilevare IP (Delphi XE)

    MrCamarium ha scritto:


    Perfetto grazie, rispetto al codice che avevo questo è più semplice e funzionale.
    mmm Non vorrei dire una cavolata, ma a me sembra lo stesso, senza lista e con le chiamate giuste....
    Nick.
  • Re: Rilevare IP (Delphi XE)

    Eh sì
Devi accedere o registrarti per scrivere nel forum
13 risposte