在SPComm这个串口通讯组件上封装了一个组件TWGComm,以存放私有通讯协议,这个组件有多个事件属性如
property OnRuntimeStatusEvent: TRuntimeStatusEvent read FOnRuntimeStatusEvent write FOnRuntimeStatusEvent;
property OnBrushCardEvent: TBrushCardEvent read FOnBrushCardEvent write FOnBrushCardEvent;
当SPComm的OnReceiveData事件激发后会激发上述事件处理过程。
上位程序通过procedure TWGComm.GetRunTimeStatus(equipNumber: DWORD);这个方法向串口发送指令后会激发上述事件。
我使用了多线程发送通讯指令给串口,如下线程执行方法代码:
procedure TControllerThread.Execute;
begin
  { Place thread code here }
   if not Assigned(FWGComm) then begin
      Suspend;
      Exit;
   end;
   
   try
      while (not Suspended) and (not Terminated) do begin
         FSection.Acquire;
         FWGComm.GetRunTimeStatus(FEquipNumber);
         FSection.Release;
         Sleep(300);
      end;
   except
      on e: Exception do
         WriteLog(e.Message,'Error');
   end;
end;
问题是当多个线程发送指令给串口时,可能会并发激活上述事件OnRuntimeStatusEvent,OnBrushCardEvent处理过程,这样应用程序会异常,如何解决,能否使同时只有一个线程激活事件?请高手指点。

解决方案 »

  1.   

    FSection.Acquire;
             FWGComm.GetRunTimeStatus(FEquipNumber);
             FSection.Release;
    你在这里做了一个重要区段加锁那你还不如把FWGComm,作为FSection的成员这样保证了FWGComm不会并行触发
      

  2.   

    这样做有无问题?
    TControllerSection = class(TCriticalSection)
       private
          FWGComm: TWGComm;
       public
          property WGComm: TWGComm read FWGComm write FWGComm;
          procedure GetRunTimeStatus(equipNumber: DWORD);
       end;procedure TControllerSection.GetRunTimeStatus(equipNumber: DWORD);
    begin
       try
          Acquire;
          FWGComm.GetRunTimeStatus(equipNumber);
       finally
          Release;
       end;
    end;procedure TControllerThread.Execute;
    begin
      { Place thread code here }
       if not Assigned(FSection.WGComm) then begin
          Suspend;
          Exit;
       end;   try
          while (not Suspended) and (not Terminated) do begin
             FSection.GetRunTimeStatus(FEquipNumber); 
             Sleep(300);
          end;
       except
          on e: Exception do
             WriteLog(e.Message,'Error');
       end;
    end;
      

  3.   

    我用Event对象解决了此问题,祝大家新年快乐!