Ver Mensaje Individual
  #1  
Antiguo 19-05-2016
oec2509 oec2509 is offline
Miembro
 
Registrado: nov 2006
Posts: 24
Reputación: 0
oec2509 Va por buen camino
Detectar ip impresra de red

Primero que nada muy buenas tardes para todos, saludos desde Costa Rica.

Tengo una aplicación que está en funcionamiento desde hace ya algunos años, se trata de un programa que esta constantemente ejecutandose a espera de ordenes de producción, cuando estas llegan, las envia a una o mas impresoras según el tipo de producto, resulta que estas impresoras son impresoras de red con una IP definida. para poder saber si la impresora está en linea se realiza un ping a la misma, si responde se envía la impresión y sino sigue chequeando cada cierto tiempo hasta que la impresora se encuentre el linea.

Para poder realizar esa verificación utilizo este utilitario:

Código Delphi [-]
unit raw_ping;

interface
uses
  Windows, SysUtils, Classes;

type
  TSunB = packed record
    s_b1, s_b2, s_b3, s_b4: byte;
  end;

  TSunW = packed record
    s_w1, s_w2: word;
  end;

  PIPAddr = ^TIPAddr;
  TIPAddr = record
    case integer of
      0: (S_un_b: TSunB);
      1: (S_un_w: TSunW);
      2: (S_addr: longword);
  end;

 IPAddr = TIPAddr;

function IcmpCreateFile : THandle; stdcall; external 'icmp.dll';
function IcmpCloseHandle (icmpHandle : THandle) : boolean; stdcall; external 'icmp.dll'
function IcmpSendEcho (IcmpHandle : THandle; DestinationAddress : IPAddr;
    RequestData : Pointer; RequestSize : Smallint;
    RequestOptions : pointer;
    ReplyBuffer : Pointer;
    ReplySize : DWORD;
    Timeout : DWORD) : DWORD; stdcall; external 'icmp.dll';


function Ping(InetAddress : string) : boolean;

procedure TranslateStringToTInAddr(AIP: string; var AInAddr);

implementation

uses
  WinSock;

function Fetch(var AInput: string; const ADelim: string = ' '; const ADelete: Boolean = true)
 : string;
var
  iPos: Integer;
begin
  if ADelim = #0 then begin
    // AnsiPos does not work with #0
    iPos := Pos(ADelim, AInput);
  end else begin
    iPos := Pos(ADelim, AInput);
  end;
  if iPos = 0 then begin
    Result := AInput;
    if ADelete then begin
      AInput := '';
    end;
  end else begin
    result := Copy(AInput, 1, iPos - 1);
    if ADelete then begin
      Delete(AInput, 1, iPos + Length(ADelim) - 1);
    end;
  end;
end;

procedure TranslateStringToTInAddr(AIP: string; var AInAddr);
var
  phe: PHostEnt;
  pac: PChar;
  GInitData: TWSAData;
begin
  WSAStartup($101, GInitData);
  try
    phe := GetHostByName(PChar(AIP));
    if Assigned(phe) then
    begin
      pac := phe^.h_addr_list^;
      if Assigned(pac) then
      begin
        with TIPAddr(AInAddr).S_un_b do begin
          s_b1 := Byte(pac[0]);
          s_b2 := Byte(pac[1]);
          s_b3 := Byte(pac[2]);
          s_b4 := Byte(pac[3]);
        end;
      end
      else
      begin
        raise Exception.Create('Error getting IP from HostName');
      end;
    end
    else
    begin
      raise Exception.Create('Error getting HostName');
    end;
  except
    FillChar(AInAddr, SizeOf(AInAddr), #0);
  end;
  WSACleanup;
end;

function Ping(InetAddress : string) : boolean;
var
 Handle : THandle;
 InAddr : IPAddr;
 DW : DWORD;
 rep : array[1..128] of byte;
begin
  result := false;
  Handle := IcmpCreateFile;
  if Handle = INVALID_HANDLE_VALUE then
   Exit;
  TranslateStringToTInAddr(InetAddress, InAddr);
  DW := IcmpSendEcho(Handle, InAddr, nil, 0, nil, @rep, 128, 0);
  Result := (DW <> 0);
  IcmpCloseHandle(Handle);
end;

end.

Este me funciono perfecto mientras lo ejecute bajo un ambiente WINDOWS SERVER 2003, ahora lo trato de ejecutar en WINDOWS 10 si siempre me devuelve como si la impresora estuviese apagada.

en esta instruccionDW := IcmpSendEcho(Handle, InAddr, nil, 0, nil, @rep, 128, 0)siempre devuelve 0 sin importar si la impresora esta apagado o no.

La verdad entiendo casi nada del código, Yo solo se que enviaba la direccion IP y me decia si estaba en línea o no

No se que buscar, para tratar de corregir esta situación, si alguien me pudiese orientar les agradeceria mucho y si alguien tuviese una rutina mas moderna para este proceso sería perfecto.

También escucho sugerencias alternativas de como resolver mi situación.

Trabajo con Delphi 2007 bajo ambiente windows server 2012 r2 y estaciones de trabajo windows 10

Nuevamente muy agradecido con la ayuda que me puedan brindar.
Responder Con Cita