powered by simpleCommunicator - 2.0.36     © 2025 Programmizd 02
Форумы / Delphi [игнор отключен] [закрыт для гостей] / не работает ping x64
25 сообщений из 41, страница 1 из 2
не работает ping x64
    #40128838
SergeyKNP
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Привет всем, ниже описанный код прекрасно работает в x32, но в x64 при ping ('test') в локальной сети в процедуре
function PingIp(Address: RawByteString): Boolean;
в строке error := GetLastError();
значение error=87 и соответственно дальше не отрабатывает

Подскажите плиз, что не так?

Код: pascal
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
29.
30.
31.
32.
33.
34.
35.
36.
37.
38.
39.
40.
41.
42.
43.
44.
45.
46.
47.
48.
49.
50.
51.
52.
53.
54.
55.
56.
57.
58.
59.
60.
61.
62.
63.
64.
65.
66.
67.
68.
69.
70.
71.
72.
73.
74.
75.
76.
77.
78.
79.
80.
81.
82.
83.
84.
85.
86.
87.
88.
89.
90.
91.
92.
93.
94.
95.
96.
97.
98.
99.
100.
101.
102.
103.
104.
105.
106.
107.
108.
109.
110.
111.
112.
113.
114.
115.
116.
117.
118.
119.
120.
121.
122.
123.
124.
125.
126.
127.
128.
129.
130.
131.
132.
133.
134.
135.
136.
137.
138.
139.
140.
141.
142.
143.
144.
145.
146.
147.
148.
149.
150.
151.
152.
153.
154.
155.
156.
157.
158.
159.
160.
161.
162.
163.
164.
unit cPing3;

interface

function Ping(Address: RawByteString): Boolean;

implementation

uses
  Windows, Winsock, SysUtils;

const
  IP_STATUS_BASE = 11000;
  IP_SUCCESS = 0;
  IP_BUF_TOO_SMALL = 11001;
  IP_DEST_NET_UNREACHABLE = 11002;
  IP_DEST_HOST_UNREACHABLE = 11003;
  IP_DEST_PROT_UNREACHABLE = 11004;
  IP_DEST_PORT_UNREACHABLE = 11005;
  IP_NO_RESOURCES = 11006;
  IP_BAD_OPTION = 11007;
  IP_HW_ERROR = 11008;
  IP_PACKET_TOO_BIG = 11009;
  IP_REQ_TIMED_OUT = 11010;
  IP_BAD_REQ = 11011;
  IP_BAD_ROUTE = 11012;
  IP_TTL_EXPIRED_TRANSIT = 11013;
  IP_TTL_EXPIRED_REASSEM = 11014;
  IP_PARAM_PROBLEM = 11015;
  IP_SOURCE_QUENCH = 11016;
  IP_OPTION_TOO_BIG = 11017;
  IP_BAD_DESTINATION = 11018;
  IP_ADDR_DELETED = 11019;
  IP_SPEC_MTU_CHANGE = 11020;
  IP_MTU_CHANGE = 11021;
  IP_UNLOAD = 11022;
  IP_GENERAL_FAILURE = 11050;
  IP_PENDING = 11255;

  MAX_IP_STATUS = IP_GENERAL_FAILURE;

type
  ip_option_information = packed record // Информация заголовка IP (Наполнение
    // этой структуры и формат полей описан в RFC791.
    Ttl: byte; // Время жизни (используется traceroute-ом)
    Tos: byte; // Тип обслуживания, обычно 0
    Flags: byte; // Флаги заголовка IP, обычно 0
    OptionsSize: byte; // Размер данных в заголовке, обычно 0, максимум 40
    OptionsData: Pointer; // Указатель на данные
  end;

  icmp_echo_reply = packed record
    Address: u_long; // Адрес отвечающего
    Status: u_long; // IP_STATUS (см. ниже)
    RTTime: u_long; // Время между эхо-запросом и эхо-ответом
    // в миллисекундах
    DataSize: u_short; // Размер возвращенных данных
    Reserved: u_short; // Зарезервировано
    Data: Pointer; // Указатель на возвращенные данные
    Options: ip_option_information; // Информация из заголовка IP
  end;

  PIPINFO = ^ip_option_information;
  PVOID = Pointer;

function IcmpCreateFile(): THandle; stdcall; external 'ICMP.DLL' name 'IcmpCreateFile';
function IcmpCloseHandle(IcmpHandle: THandle): BOOL; stdcall; external 'ICMP.DLL' name 'IcmpCloseHandle';
function IcmpSendEcho(IcmpHandle: THandle; // handle, возвращенный IcmpCreateFile()
  DestAddress: u_long; // Адрес получателя (в сетевом порядке)
  RequestData: PVOID; // Указатель на посылаемые данные
  RequestSize: Word; // Размер посылаемых данных
  RequestOptns: PIPINFO; // Указатель на посылаемую структуру
  // ip_option_information (может быть nil)
  ReplyBuffer: PVOID; // Указатель на буфер, содержащий ответы.
  ReplySize: DWORD; // Размер буфера ответов
  Timeout: DWORD // Время ожидания ответа в миллисекундах
  ): DWORD; stdcall; external 'ICMP.DLL' name 'IcmpSendEcho';

function PingIp(Address: RawByteString): Boolean;
var
  hIP: THandle;
  pingBuffer: array of AnsiChar;
  pIpe: ^icmp_echo_reply;
  wVersionRequested: Word;
  lwsaData: WSAData;
  error: DWORD;
  DestAddress: In_Addr;
begin

  Result := False;
  hIP := IcmpCreateFile();
  GetMem(pIpe, sizeof(icmp_echo_reply) + Length(pingBuffer));
  try
    pIpe.Data := @pingBuffer;
    pIpe.DataSize := Length(pingBuffer);

    wVersionRequested := MakeWord(1, 1);
    error := WSAStartup(wVersionRequested, lwsaData);
    if (error <> 0) then
    begin
      Exit;
    end;
    DestAddress.S_addr := inet_addr(PAnsiChar(Address));
    IcmpSendEcho(hIP, DestAddress.S_addr, @pingBuffer, Length(pingBuffer), Nil, pIpe, sizeof(icmp_echo_reply) + Length(pingBuffer), 1000);

    error := GetLastError();
    if (error <> 0) then
    begin
      Exit;
    end;
    Result := pIpe.Status = IP_SUCCESS;
  finally
    IcmpCloseHandle(hIP);
    WSACleanup();
    FreeMem(pIpe);
  end;
end;

function HostToIP(name: RawByteString; var Ip: RawByteString): Boolean;
var
  wsdata: TWSAData;
  hostName: array [0 .. 255] of AnsiChar;
  hostEnt: PHostEnt;
  addr: PAnsiChar;
begin
  WSAStartup($0101, wsdata);
  try
    gethostname(@hostName[0], sizeof(hostName));
    StrPCopy(hostName, name);
    hostEnt := gethostbyname(hostName);
    if Assigned(hostEnt) then
      if Assigned(hostEnt^.h_addr_list) then
      begin
        addr := hostEnt^.h_addr_list^;
        if Assigned(addr) then
        begin
          Ip := Format('%d.%d.%d.%d', [byte(addr[0]), byte(addr[1]), byte(addr[2]), byte(addr[3])]);
          Result := True;
        end
        else
          Result := False;
      end
      else
        Result := False
    else
    begin
      Result := False;
    end;
  finally
    WSACleanup;
  end
end;

function Ping(Address: RawByteString): Boolean;
var
  s: RawByteString;

begin
  Result := HostToIP(Address, s);
  if Result then
    Result := PingIp(s);
end;

end.

...
Рейтинг: 0 / 0
не работает ping x64
    #40128842
Siemargl
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
SergeyKNP,

из-за смены битности поплыли размеры указателей и структур. внимательно см msdn, там есть нужные примечания

еще тут почитай
https://stackoverflow.com/questions/51087679/winapi-icmpsendecho-on-64-bit-platform
...
Рейтинг: 0 / 0
не работает ping x64
    #40128845
SergeyKNP
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Siemargl

из-за смены битности поплыли размеры указателей и структур. внимательно см msdn, там есть нужные примечания

еще тут почитай
https://stackoverflow.com/questions/51087679/winapi-icmpsendecho-on-64-bit-platform


читал...но нельзя ли поправить сам код который я привёл?
...
Рейтинг: 0 / 0
не работает ping x64
    #40128846
Фотография _Vasilisk_
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Пробежал глазами. Первое, что бросилось в глаза - packed. Его нужно убрать
...
Рейтинг: 0 / 0
не работает ping x64
    #40128847
SergeyKNP
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
было
IcmpSendEcho(hIP, DestAddress.S_addr, @pingBuffer, sizeof(pingBuffer), Nil, pIpe, sizeof(icmp_echo_reply) + sizeof(pingBuffer), 10);


поправил на ...добавил +8
IcmpSendEcho(hIP, DestAddress.S_addr, @pingBuffer, sizeof(pingBuffer), Nil, pIpe, sizeof(icmp_echo_reply) + sizeof(pingBuffer)+8, 10);

теперь работает
...
Рейтинг: 0 / 0
не работает ping x64
    #40128848
Соколинский Борис
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
_Vasilisk_
Пробежал глазами. Первое, что бросилось в глаза - packed. Его нужно убрать
Зачем?
Разработчиков API, работающих с хрен-знает-как выравненными структурами нужно убивать на месте а не поощрять.
...
Рейтинг: 0 / 0
не работает ping x64
    #40128849
SergeyKNP
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
Соколинский Борис,

может предложишь свой вариант КОНКРЕТНОГО кода?
...
Рейтинг: 0 / 0
не работает ping x64
    #40128850
asutp2
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
_Vasilisk_
Пробежал глазами. Первое, что бросилось в глаза - packed. Его нужно убрать
С чего это вдруг? ты предлагаешь отдать на откуп компилятору и директиве выравнивания расположение полей в рекорде?))))

SergeyKNP, не мучайся, проcто используй Indy
...
Рейтинг: 0 / 0
не работает ping x64
    #40128858
Siemargl
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
SergeyKNP
Siemargl

из-за смены битности поплыли размеры указателей и структур. внимательно см msdn, там есть нужные примечания

еще тут почитай
https://stackoverflow.com/questions/51087679/winapi-icmpsendecho-on-64-bit-platform


читал...но нельзя ли поправить сам код который я привёл?

Можно. Правь.
...
Рейтинг: 0 / 0
не работает ping x64
    #40128861
Kazantsev Alexey
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
SergeyKNP
Подскажите плиз, что не так?

Убери packed ;
...
Рейтинг: 0 / 0
не работает ping x64
    #40128887
SergeyKNP
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Гость
"Siemargl,
Можно. Правь."

особо одарённые, такие как ты, пусть не возбуждаются и идут лесом.
...
Рейтинг: 0 / 0
не работает ping x64
    #40128902
Фотография _Vasilisk_
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
asutp2
ты предлагаешь отдать на откуп компилятору и директиве выравнивания расположение полей в рекорде?))))
Я предлагаю использовать единые стандарты выравнивания при портировании кода. В данном случае должно быть
Код: pascal
1.
{$ALIGN 8}

и оно же, о чудо!, совпадает с дефолтным значением.
...
Рейтинг: 0 / 0
не работает ping x64
    #40128903
Фотография _Vasilisk_
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Соколинский Борис
работающих с хрен-знает-как выравненными структурами
Не хрен-знает-как выравненными, а дефолтным 8. Причем этот дефолт что в Делфи, что в Си. Не нравится дефолт - пропиши явно
Код: pascal
1.
{$ALIGN 8}

но packed - это полный бред
...
Рейтинг: 0 / 0
не работает ping x64
    #40128904
asutp2
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
_Vasilisk_
asutp2
ты предлагаешь отдать на откуп компилятору и директиве выравнивания расположение полей в рекорде?))))
Я предлагаю использовать единые стандарты выравнивания при портировании кода. В данном случае должно быть
Код: pascal
1.
{$ALIGN 8}

и оно же, о чудо!, совпадает с дефолтным значением.
А ты полностью уверен, что Microsoft во всех вызовах API использует исключительно выровненные структуры $ALIGN 8 ?))
...
Рейтинг: 0 / 0
не работает ping x64
    #40128907
Dimitry Sibiryakov
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Это легко проверяется чтением их объявления в заголовках SDK.
Posted via ActualForum NNTP Server 1.5
...
Рейтинг: 0 / 0
не работает ping x64
    #40128911
asutp2
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Dimitry Sibiryakov

Это легко проверяется чтением их объявления в заголовках SDK.
вот именно, сначала нужно смотреть описание в SDK и после этого использовать требуемое выравнивание либо packed

Вот пример структуры, которая в Win64 требует именно $ALIGN 4
...
Рейтинг: 0 / 0
не работает ping x64
    #40128934
Соколинский Борис
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
_Vasilisk_
Соколинский Борис
работающих с хрен-знает-как выравненными структурами
Не хрен-знает-как выравненными, а дефолтным 8. Причем этот дефолт что в Делфи, что в Си.
Неужели?

Код: pascal
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
program PacketSize;
{$APPTYPE CONSOLE}
uses
  SysUtils;

type
  TByteRecord = record
    a,b,c: byte;
  end;

  TMixedRecord = record
    a,b: integer;
    d: byte;
  end;

begin
  Write('Byte record: ');
  WriteLn(SizeOf(TByteRecord));
  Write('Mixed record: ');
  WriteLn(SizeOf(TMixedRecord));
  ReadLn;
end.


Давай навскидку: что будет выведено?

_Vasilisk_
но packed - это полный бред
Бред - это использовать в межмодульных коммуникациях структуры переменного размера.
...
Рейтинг: 0 / 0
не работает ping x64
    #40128960
Kazantsev Alexey
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Когда требуется конкретное выравнивание задавайте его руками. О чём копья ломать...
Код: pascal
1.
2.
3.
4.
5.
6.
7.
8.
type
 struct1 = record
  ...
 end align 4;

 struct2 = record
  ...
 end align 8;
...
Рейтинг: 0 / 0
не работает ping x64
    #40128963
Соколинский Борис
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
На самом деле выравнивание структур существенно только когда их размер меньше разрядности регистров, чтобы операции присваивания за один такт выполнялись.
Кратность адреса в плане быстродействия дает прирост в копейки.
...
Рейтинг: 0 / 0
не работает ping x64
    #40128997
Фотография _Vasilisk_
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Соколинский Борис
Давай навскидку: что будет выведено?
ByteRecord - 4, Mixed - 12
...
Рейтинг: 0 / 0
не работает ping x64
    #40128998
Фотография _Vasilisk_
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Kazantsev Alexey
Код: pascal
1.
2.
3.
struct1 = record
  ...
 end align 4;

Это официальный синтаксис? Первый раз такое вижу
...
Рейтинг: 0 / 0
не работает ping x64
    #40129000
Соколинский Борис
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
_Vasilisk_
Соколинский Борис
Давай навскидку: что будет выведено?
ByteRecord - 4, Mixed - 12

Код: plaintext
1.
2.
Byte record: 3
Mixed record: 12

Т.е. "default 8" на поверку оказывается совсем не default и логика выравнивания весьма неоднозначная.
И когда предлагается поверить, что неизвестно какой компилятор библиотеки использует такую же, нормальный ответ будет - "не надо выпендрежей, используйте packed record и #pragma pack(1)
...
Рейтинг: 0 / 0
не работает ping x64
    #40129001
s62
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Соколинский Борис
Бред - это использовать в межмодульных коммуникациях структуры переменного размера.
Ну так это же не свой самописный код, а структуры, определенные Майкрософтом . Как MS задал, так и надо использовать. Кстати эти структуры/записи есть в исходниках Delphi, файл unit Winapi.IpExport. Там - не упакованные.

Код: pascal
1.
2.
3.
4.
5.
6.
7.
8.
9.
10.
11.
12.
13.
14.
15.
16.
17.
18.
19.
20.
21.
22.
23.
24.
25.
26.
27.
28.
29.
30.
31.
32.
33.
type
  IP_OPTION_INFORMATION = record
    Ttl: UCHAR;          // Time To Live
    Tos: UCHAR;          // Type Of Service
    Flags: UCHAR;        // IP header flags
    OptionsSize: UCHAR;  // Size in bytes of options data
    OptionsData: PUCHAR; // Pointer to options data
  end;
  {$EXTERNALSYM IP_OPTION_INFORMATION}
  PIP_OPTION_INFORMATION = ^IP_OPTION_INFORMATION;
  {$EXTERNALSYM PIP_OPTION_INFORMATION}
  TIpOptionInformation = IP_OPTION_INFORMATION;
  PIpOptionInformation = PIP_OPTION_INFORMATION;

//
// The icmp_echo_reply structure describes the data returned in response
// to an echo request.
//

  ICMP_ECHO_REPLY = record
    Address: IPAddr;      // Replying address
    Status: ULONG;        // Reply IP_STATUS
    RoundTripTime: ULONG; // RTT in milliseconds
    DataSize: USHORT;     // Reply data size in bytes
    Reserved: USHORT;     // Reserved for system use
    Data: LPVOID;         // Pointer to the reply data
    Options: ip_option_information; // Reply options
  end;
  {$EXTERNALSYM ICMP_ECHO_REPLY}
  PICMP_ECHO_REPLY = ^ICMP_ECHO_REPLY;
  {$EXTERNALSYM PICMP_ECHO_REPLY}
  TIcmpEchoReply = ICMP_ECHO_REPLY;
  PIcmpEchoReply = PICMP_ECHO_REPLY;



p.s. Почитал по своей же ссылке, пишут, что для 64 бит надо использовать вот такую структуру:
https://docs.microsoft.com/en-us/windows/win32/api/ipexport/ns-ipexport-icmp_echo_reply32
...
Рейтинг: 0 / 0
не работает ping x64
    #40129002
Dimitry Sibiryakov
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
Выравнивание размера структуры и выравнивание её полей это как бы две разные
вещи. Попробуйте sizeof от массива TByteRecord для пущей занимательности.
Posted via ActualForum NNTP Server 1.5
...
Рейтинг: 0 / 0
не работает ping x64
    #40129005
Kazantsev Alexey
Скрыть профиль Поместить в игнор-лист Сообщения автора в теме
Участник
_Vasilisk_
Это официальный синтаксис? Первый раз такое вижу

Ну, как сказать... В доке такого нет, но в исходниках встречается со времён XE2. Даже FPC в режиме совместимости с дельфями это поддерживает. Начиная с Сиэтла (10.0) появился ещё и атрибут [Align(N)].
...
Рейтинг: 0 / 0
25 сообщений из 41, страница 1 из 2
Форумы / Delphi [игнор отключен] [закрыт для гостей] / не работает ping x64
Целевая тема:
Создать новую тему:
Автор:
Закрыть
Цитировать
Найденые пользователи ...
Разблокировать пользователей ...
Читали форум (0):
Пользователи онлайн (0):
x
x
Закрыть


Просмотр
0 / 0
Close
Debug Console [Select Text]