delphi - How do I reset a buffer of indy UDP client? - Stack Overflow

I noticed a little issue with Indy's TIdSNTP:If the timeout is less than actual network delay, wh

I noticed a little issue with Indy's TIdSNTP: If the timeout is less than actual network delay, when doing DateTime request, the datagram is not received in timeout time;

however this old datagram is kept in some internal buffer and next call to the DateTime receives this old datagram, giving wrong time value.

  var sntp1: TIdSNTP := TIdSNTP.Create;
  sntp1.Host := 'pool.ntp';
  sntp1.ReceiveTimeout := 5;
  sntp1.DateTime;
  Memo1.Lines.Add(Format(' delay: %d', [ round(sntp1.RoundTripDelay * MSecsPerDay) ]));
  Application.ProcessMessages;
  sleep(3000);
  sntp1.ReceiveTimeout := 500;
  sntp1.DateTime;
  Memo1.Lines.Add(Format(' delay: %d', [ round(sntp1.RoundTripDelay * MSecsPerDay) ]));

The question is, how do I properly reset the buffer to clear old pending data, before next call to DateTime ?

I noticed a little issue with Indy's TIdSNTP: If the timeout is less than actual network delay, when doing DateTime request, the datagram is not received in timeout time;

however this old datagram is kept in some internal buffer and next call to the DateTime receives this old datagram, giving wrong time value.

  var sntp1: TIdSNTP := TIdSNTP.Create;
  sntp1.Host := 'pool.ntp.';
  sntp1.ReceiveTimeout := 5;
  sntp1.DateTime;
  Memo1.Lines.Add(Format(' delay: %d', [ round(sntp1.RoundTripDelay * MSecsPerDay) ]));
  Application.ProcessMessages;
  sleep(3000);
  sntp1.ReceiveTimeout := 500;
  sntp1.DateTime;
  Memo1.Lines.Add(Format(' delay: %d', [ round(sntp1.RoundTripDelay * MSecsPerDay) ]));

The question is, how do I properly reset the buffer to clear old pending data, before next call to DateTime ?

Share Improve this question asked Jan 29 at 12:10 SargisSargis 2032 silver badges10 bronze badges 1
  • 1 As a workaround, you may create a new instance of the TIdSNTP before every usage. And free the previous, of course. – mjn Commented Jan 29 at 12:16
Add a comment  | 

1 Answer 1

Reset to default 2

You are reusing the same underlying socket for both TIdSNTP.DateTime queries, which is why the packet is able to be cached inside the socket.

You should re-create the TIdSNTP object each time, or at least close its current socket with TIdSNTP.Binding.CloseSocket() so the next query will create a new socket.

You could try flushing the socket buffer manually, by reading directly from the TIdSNTP.Binding socket until there is nothing left to read. But this is still a race condition if a new packet arrives after you flush but before you perform the next query. So better to just discard the socket altogether to throw away the current buffer.

发布者:admin,转转请注明出处:http://www.yc00.com/questions/1745299215a4621332.html

相关推荐

  • delphi - How do I reset a buffer of indy UDP client? - Stack Overflow

    I noticed a little issue with Indy's TIdSNTP:If the timeout is less than actual network delay, wh

    12小时前
    50

发表回复

评论列表(0条)

  • 暂无评论

联系我们

400-800-8888

在线咨询: QQ交谈

邮件:admin@example.com

工作时间:周一至周五,9:30-18:30,节假日休息

关注微信