Changeset 302 for PinConnection


Ignore:
Timestamp:
Dec 5, 2011, 2:20:39 PM (13 years ago)
Author:
chronos
Message:
  • Fixed: CommThread delay in loop only if necessery.
  • Modified: CommDelay now use two separated thread for both direction.
Location:
PinConnection
Files:
2 edited

Legend:

Unmodified
Added
Removed
  • PinConnection/UCommDelay.pas

    r296 r302  
    2424  TCommDelayThread = class(TTermThread)
    2525    Parent: TCommDelay;
     26    PacketQueue: TListObject;
     27    Pin: TCommPin;
     28    Lock: TCriticalSection;
    2629    procedure Execute; override;
    2730  end;
     
    3538    PacketQueue1: TListObject; // TListObject<TDelayedPacket>
    3639    PacketQueue2: TListObject; // TListObject<TDelayedPacket>
    37     Thread: TCommDelayThread;
     40    Thread1: TCommDelayThread;
     41    Thread2: TCommDelayThread;
    3842    procedure ReceiveData1(Sender: TCommPin; AStream: TStream);
    3943    procedure ReceiveData2(Sender: TCommPin; AStream: TStream);
    4044    procedure SetActive(AValue: Boolean);
    4145  public
    42     Lock: TCriticalSection;
     46    Lock1: TCriticalSection;
     47    Lock2: TCriticalSection;
    4348    Pin1: TCommPin;
    4449    Pin2: TCommPin;
     
    5863  CurrentTime: TDateTime;
    5964  SendData: TStreamHelper;
     65  DoSleep: Boolean;
    6066begin
    6167  try
    6268    SendData := TStreamHelper.Create;
    6369    repeat
    64       with Parent do begin
     70      DoSleep := True;
    6571        try
    6672          Lock.Acquire;
    6773          CurrentTime := Now;
    68           for I := PacketQueue1.Count - 1 downto 0 do
    69             if TDelayedPacket(PacketQueue1[I]).ReceiveTime < (CurrentTime - Delay) then begin
     74          I := 0;
     75          while (I < PacketQueue.Count) do
     76            if TDelayedPacket(PacketQueue[I]).ReceiveTime < (CurrentTime - Parent.Delay) then begin
     77              DoSleep := False;
    7078              SendData.Clear;
    71               SendData.WriteStream(TDelayedPacket(PacketQueue1[I]).Data, TDelayedPacket(PacketQueue1[I]).Data.Size);
    72               PacketQueue1.Delete(I);
     79              SendData.WriteStream(TDelayedPacket(PacketQueue[I]).Data, TDelayedPacket(PacketQueue[I]).Data.Size);
     80              PacketQueue.Delete(I);
    7381              try
    7482                Lock.Release;
    75                 Pin1.Send(SendData.Stream);
     83                Pin.Send(SendData.Stream);
    7684              finally
    7785                Lock.Acquire;
    7886              end;
    79             end;
    80 
    81           for I := PacketQueue2.Count - 1 downto 0 do
    82             if TDelayedPacket(PacketQueue2[I]).ReceiveTime < (CurrentTime - Delay) then begin
    83               SendData.Clear;
    84               SendData.WriteStream(TDelayedPacket(PacketQueue2[I]).Data, TDelayedPacket(PacketQueue2[I]).Data.Size);
    85               PacketQueue2.Delete(I);
    86               try
    87                 Lock.Release;
    88                 Pin2.Send(SendData.Stream);
    89               finally
    90                 Lock.Acquire;
    91               end;
    92             end;
     87            end else Inc(I);
    9388        finally
    9489          Lock.Release;
    9590        end;
    96       end;
    97       if not Terminated then Sleep(1);
     91      if not Terminated and DoSleep then Sleep(1);
    9892    until Terminated;
    9993  finally
     
    120114begin
    121115  try
    122     Lock.Acquire;
     116    Lock2.Acquire;
    123117    if Delay = 0 then Pin2.Send(AStream)
    124118    else
     
    128122    end;
    129123  finally
    130     Lock.Release;
     124    Lock2.Release;
    131125  end;
    132126end;
     
    135129begin
    136130  try
    137     Lock.Acquire;
     131    Lock1.Acquire;
    138132    if Delay = 0 then Pin1.Send(AStream)
    139133    else
     
    143137    end;
    144138  finally
    145     Lock.Release;
     139    Lock1.Release;
    146140  end;
    147141end;
     
    152146  FActive := AValue;
    153147  if AValue then begin
    154     Thread := TCommDelayThread.Create(True);
    155     Thread.FreeOnTerminate := False;
    156     Thread.Parent := Self;
    157     Thread.Name := 'CommDelay';
    158     Thread.Start;
     148    Thread1 := TCommDelayThread.Create(True);
     149    Thread1.FreeOnTerminate := False;
     150    Thread1.Parent := Self;
     151    Thread1.Name := 'CommDelay1';
     152    Thread1.PacketQueue := PacketQueue1;
     153    Thread1.Pin := Pin1;
     154    Thread1.Lock := Lock1;
     155    Thread1.Start;
     156
     157    Thread2 := TCommDelayThread.Create(True);
     158    Thread2.FreeOnTerminate := False;
     159    Thread2.Parent := Self;
     160    Thread2.Name := 'CommDelay2';
     161    Thread2.PacketQueue := PacketQueue2;
     162    Thread2.Pin := Pin2;
     163    Thread2.Lock := Lock2;
     164    Thread2.Start;
    159165  end else begin
    160     FreeAndNil(Thread);
     166    FreeAndNil(Thread1);
     167    FreeAndNil(Thread2);
    161168  end;
    162169end;
     
    164171constructor TCommDelay.Create;
    165172begin
    166   Lock := TCriticalSection.Create;
     173  Lock1 := TCriticalSection.Create;
     174  Lock2 := TCriticalSection.Create;
    167175  PacketQueue1 := TListObject.Create;
    168176  PacketQueue2 := TListObject.Create;
     
    180188  PacketQueue1.Free;
    181189  PacketQueue2.Free;
    182   Lock.Free;
     190  Lock1.Free;
     191  Lock2.Free;
    183192  inherited Destroy;
    184193end;
  • PinConnection/UCommThread.pas

    r296 r302  
    139139var
    140140  TempStatus: Integer;
     141  DoSleep: Boolean;
    141142begin
    142143  with Parent do
    143144  repeat
     145    DoSleep := True;
    144146    // Check if new data arrived
    145     if FDataAvailable.WaitFor(1) = wrSignaled then begin
     147    if FDataAvailable.WaitFor(0) = wrSignaled then begin
     148      DoSleep := False;
    146149      try
    147150        FInputBufferLock.Acquire;
     
    158161    // Check if state changed
    159162    if FStatusEvent.WaitFor(0) = wrSignaled then begin
     163      DoSleep := False;
    160164      try
    161165        FInputBufferLock.Acquire;
     
    166170      end;
    167171      Pin.Status := TempStatus;
     172    end;
     173    if not Terminated and DoSleep then begin
     174      Sleep(1);
    168175    end;
    169176  until Terminated;
Note: See TracChangeset for help on using the changeset viewer.