2010-06-11 78 views
3

我們正在開發一個軟件來控制一個科學的測量設備。它提供了一個COM-Interface定義了幾個功能來設置測量參數並在測量數據時觸發一個事件。C#COM跨線程

爲了測試我們的軟件,我正在實現該設備的模擬。

com對象運行一個定期觸發事件的循環。客戶端應用程序中的另一個循環現在應該使用給定的函數來設置com模擬器。

我創建了一個測量參數的類,它將在設置新測量時實例化。

// COM-Object 
public class MeasurementParams 
{ 
    public double Param1; 
    public double Param2; 
} 

public class COM_Sim : ICOMDevice 
{ 
    public MeasurementParams newMeasurement; 
    IClient client; 

    public int NewMeasurement() 
    { 
     newMeasurment = new MeasurementParam(); 
    } 

    public int SetParam1(double val) 
    { 
     // why is newMeasurement null when method is called from client loop 
     newMeasurement.Param1 = val; 
    } 

    void loop() 
    { 
     while(true) 
     { 
      // fire event 
      client.HandleEvent; 
     } 
    } 
} 

public class Client : IClient 
{ 
    ICOMDevice server; 

    public int HandleEvent() 
    { 
     // handle this event 
     server.NewMeasurement(); 
     server.SetParam1(0.0); 
    } 

    void loop() 
    { 
     while(true) 
     { 
      // do some stuff... 
      server.NewMeasurement(); 
      server.SetParam1(0.0); 
     } 
    } 
} 

這兩個循環都在獨立線程中運行。當server.NewMeasurement()被調用時,服務器上的對象被設置爲一個新的實例。但在下一個函數中,該對象再次爲空。在處理服務器事件時做同樣的事情,它完美地工作,因爲方法在服務器線程中運行。如何使它從客戶端線程工作。

由於客戶端旨在與真實設備一起工作,因此我無法修改製造商提供的接口。我還需要設置獨立於事件處理程序的度量,該度量將不會定期觸發。

我認爲這個問題與多線程COM行爲有關,但是我沒有在這個主題上發現任何東西。

回答

1

什麼是客戶端和服務器的線程模型 - STA或MTA? (僅供參考 - STA是單線程Com對象,用於允許一次只從一個線程訪問其公共方法,MTA是多線程對象,允許從多個線程同時訪問其公共方法)

你對他們每個人有多少實例?你如何創建這些實例?我懷疑你只想要一個,但你最後會以多個結束。

你有多少個線程,哪個線程上運行着哪個方法?你如何創建這些線程,並初始化它們以運行STA對象或MTA?

說明: .NET足夠智能,可以檢測客戶端和服務器是否都受到管理,並且會將COM從圖片中提取出來。所以,你的模擬運行純粹的託管代碼。如果你想要正確的測試客戶端,你需要把它寫成C++(因爲我懷疑你的設備控制器是非託管代碼)。有關COM線程模型

參考文檔:

Understanding and Using COM Threading Models
Processes, Threads and Appartments
Introduction to COM Interop

+0

感謝。我錯過了明確地將服務器環路設置爲MTA。 – user364676 2010-06-11 16:40:35

+0

當然你想這樣做?你的代碼不是線程安全的。 – 2010-06-11 16:44:04

1

在您發佈的代碼中,COM_Sim.client從不分配。有什麼遺漏嗎?沒有看到對象是如何分配的,很難診斷。

此外:您目前有newMeasurementCOM_Sim中聲明爲公共字段,但newMeasurment(拼寫不同)在方法內。正如所寫的,這段代碼不會編譯。您的實際方法中可能存在類似的拼寫錯誤,導致您將其分配給與您認爲在NewMeasurement內部創建的對象不同的對象。