程焱明
(中國船舶重工集團公司第七二三研究所 江蘇省揚州市 225011)
原生定時器(Windows 系統)、基于線程的定時器、面向對象的定時器均屬于傳統的定時器模型,但這類定時器很容易在應用中出現定時器失效、程序結構混亂、軟件可讀性下降等問題。為保證定時器更好服務于電子戰指控系統開發,正是本文圍繞該課題開展具體研究的原因所在。
電子戰軟件中的傳統定時器模型種類多樣,代表性較高的可細分為三類,包括原生定時器、基于線程的定時器、面向對象的定時器,這類定時器存在的優勢和不足必須得到重點關注。
Windows 系統存在原生定時器,該定時器看起來較為簡單,如在指定的窗口進行定時器回調操作注冊,做好間隔時間設定,并最終響應系統WM-TIMER 消息即可,通常情況下原生定時器可滿足相關需要。但對于電子戰指控系統來說,其本身對實時性存在較強要求,這種情況下原生定時器的應用很容易引發意想不到的問題。原生定時器的回調處理基于響應WM-TIMER 消息實現,但由于WM-TIMER 消息處理在Windows 系統中的優先級較低,在其它窗口消息存在于應用程序消息隊列中時,WM-TIMER 消息調度會被操作系統忽視,系統在指定時刻點上未能及時執行處理回調的情況很容易出現。對于應用程序不停接收通信鏈路數據的情況,由于系統需要對收到的數據進行迅速處理并不停響應網絡消息,此時定時器回調操作將沒有機會執行,原生定時器會因此失效[1]。
為突破原生定時器性能瓶頸,基于多線程技術的定時器模型探索長期受到重視,通過開辟新的工作者線程獨立于主線程外,基于系統API 應用程序接口,新線程內部即可實現手工定時計數,在指定的間隔時間達到后,實際的定時回調操作即可由收到通知的外部主線程完成。基于線程的定時器在理論上可行的,在具體的實踐應用中也取得了不俗效果。但值得注意的是,基于線程的定時器涉及線程同步、線程通信、線程創建等多線程編程技術,死鎖情況也很容易出現于線程同步過程中,這對開發人員提出了較高挑戰。對于需要使用多個定時器的電子戰軟件開發來說,如無法科學組織各定時器,將導致非常混亂的程序結構出現,更為復雜的控制流程會直接影響軟件開發[2]。

圖1:組件式定時器的內部結構
為更好服務于軟件開發,面向對象技術也被引入定時器領域,由此封裝基于線程的定時器,C++的封裝類得以產生,系統的健壯性可大幅提升。但對于規模不斷變大的軟件來說,愈加復雜的流程使得簡單封裝無法滿足實際需要。對于具備“對實現的封裝”特點的C++語言來說,與具體實現相關的代碼大量存在于封裝類中,同時與業務邏輯的聯系較少。大量零散的封裝類混雜于軟件結構中,軟件可讀性因此下降。此外,其他語言中C++語言編寫的封裝類無法直接影響,多語言協同開發因此受到的影響必須得到重視,對于整個電子戰軟件來說,某些部分存在性能上較高指標,具體實現需使用C/C++等編譯性的語言,也有一些部分需要華麗的用戶界面、較快的開發速度且對性能要求較低,具體實現可采用ASP、VB 等存在較高靈活性的解釋性語言。在集成軟件過程中,最終軟件產品需結合各方面形成,考慮到不同的開發語言中定時器等具有共性的功能模塊需設法集成,由此引發的定時器跨語言問題必須得到重視。
為彌補電子戰軟件中的傳統定時器模型存在的缺陷,本文引入了組件式開發技術,通過對基于線程的定時器進行封裝即可同時提供跨語言解決方案。需要將龐大、單獨、復雜的應用程序劃分為多個模塊,并應用組件化程序設計思想,此時模塊不能被簡單的視作代碼集合,而是真正成為自給自足的組件,同一臺機器上可允許這類組件,廣域網、局域網、Internet 的不同機器上也可允許這類組件。分析理性化的組件系統可以發現,組件內部的結構無需被用戶了解,所需工作可通過配置組件完成。為實現組件化軟件開發,CORBA公共對象請求代理體系結構由OMG 對象管理組織提出,UNIX 操作系統屬于該結構的主要應用平臺。微軟在Windows 平臺上提出了COM 標準組件對象模型,組件之間交互的規范由此明確,實現交互的環境也同時提供。對于不依賴于任何特定語言的組件對象之間交互來說,COM 可作為一種標準用于不同語言協作開發。
深入分析可以發現,組件式軟件開發具備四方面優勢,包括容易替換、能夠較好適應需求變化、可實現二進制代碼重用、較好服務于并行開發。所謂容易替換,指的是組件式開發技術可將龐大復雜的企業級應用系統劃分為多個組件模塊,在版本升級和系統修改時,可對相應組件進行替換或修改,其他部分不會受到影響;基于適應需求變化進行分析可以發現,不明確的業務需求在軟件開發中較為常見,新的需求會在軟件配置及開發過程中不斷出現,而在組件式開發技術支持下,通過在少數幾個組件中存放業務規則,即可通過重建并發布新組件或修改相關組件更好適應業務規則,局部更新可同時在局部中局限出錯機會,軟件測試和調試的便利性將大幅提升;分析可實現二進制代碼重用可以發現,二進制級別上的重用和集成可通過組件式開發實現,即一次編寫代碼的多處使用,多個團隊使用不同開發工具的協同工作可更好完成。如高實時性的算法分析組件由C++開發團隊開發,使用該組件的VB 開發團隊無需進行組件對應VB 版本的針對性開發,而是可以在同一個操作系統平臺下直接使用,這是由于組件為二進制級別重用的;分析較好服務于并行開發可以發現,對于由許多組件構成的大應用系統來發,可同時進行這類組件的開發。在具體開發過程中,需劃分業務邏輯為多個不同的組件,隨后進行接口的針對性設計,即可由開發團隊并行開發,各個組件可最終在系統集成階段順利集成[3]。
圖1為組件式定時器的內部結構,具體設計基于COM 開展,定時器的內部由COM 技術封裝,二進制級的代碼重用的支持也同時實現。整個組件對外導出接口4 個,即IUnknown、ISyncNotify、IAsyncNotify、IDispatch。
2.2.1 IUnknown 接口
分析IUnknown 接口可以發現,每個COM 組件均必須導出該接口,其他所有接口的繼承也需要基于IUnknown 接口實現,可見所有COM 接口的根為IUnknown 接口。IUnknown 接口共存在函數3 個,提供接口查詢和組件的生存期控制兩個重要功能。外部用戶對組件的使用情況可基于Release 和Ad-dRef 確定,具體需要對組件內部的成員變量m_cRef 進行操作,組件生存期控制可由此實現。如存在減為0 的該變量,則說明組件沒有其它用戶使用,自身所占據的系統資源即可由組件自動釋放,包括系統句柄等、內存、數據庫等。在實例化1 個組件出來后,外部用戶開始可得到1 個IUnknown 接口,為滿足實際應用需要,接口查詢需采用QueryInterface。如接口能夠由組件支持,1 個結果接口指針會隨之返回,組件功能可由用戶進一步調用。
2.2.2 ISyncNotify 和IAsyncNotify 接口
分析ISyncNotify 和IAsyncNotify 接口可以發現,具體的定時器邏輯由兩個接口實現。為方便使用并保持一致,采用相同結構設計2 個接口,因此對于用戶存在一致的調用方式,具體差異存在于實現的功能上。ISyncNotify 接口的定時器通知采用同步的方式,IAsyncNotify 接口的定時器通知采用異步方式。基于調用約定進行操作,事件的通知消息即可在指定的定時器間隔時刻點獲得。RegisterNotify 為請求組件注冊新的定時器通知事件,以ms 為單位的定時器間隔時間由interval 給出,umsg、hwnd 分別為通知消息和通知窗口。在注冊成功后,定時器通知的句柄為pid 接收的1 個ID。參數ID、UnregisterNotify 分別為定時器通知句柄、請求組件刪除指定的定時器通知事件。具體的接口實現需開辟工作者線程,每個同步定時器均需要開辟1 個,定時器事件通知可由此實現,整個系統中其它定時器工作因一個定時器事件處理阻塞而出現異常也可同時規避。對于不涉及到阻塞問題的異步定時器來說,考慮到其需要負責一個通知消息的簡單投遞,因此公共工作者線程的開辟極為關鍵。需充分考慮事件通知、定時計數、線程同步、優先級等復雜的控制流程,在COM組件的封裝下,使用便利性提升可同時實現。
2.2.3 IDispatch 接口
IDispatch 接口屬于支持自動化的核心接口,該接口在1 個數組中集中所有成員函數的入口地址,并在內部維護1 個映射表。根據序號索引,外部用戶可快速找到需要的函數并進行相應功能執行。對于HTML、ASP、VB 等解釋性語言,以及Excel、Word 等包公軟件提供的“宏”功能,均可對組件自動化接口進行較好訪問。IDispatch 接口提供的函數可用于組件支持的所有類型庫信息查詢,組件瀏覽器枚舉訪問的便利性可大幅提升。此外,基于函數名稱查詢索引編號、具體的函數調用執行、遠程計算機上組件接口函數調用也可基于IDispatch 接口實現,由此需要調用的函數名稱可在運行時動態指定,需要調用的函數不必事先明確,動態綁定可由此完成。IDispatch 接口在組件式定時器中的實現可較好服務于使用ASP、VB 進行軟件開發的團隊,協同開發可由此更為便利開展。
結合實際調研可以發現,結合組件式開發思想設計的組件式定時器現階段已在我國大型電子戰指揮系統中實現廣泛、成功應用,組件式定時器在系統中的運行極為穩定,組件式開發技術的應用價值由此得到證明。
綜上所述,電子戰軟件中組件式定時器開發需關注多方面因素影響。在此基礎上,本文涉及的組件式軟件開發、組件式定時器的設計、組件式定時器的應用等內容,則直觀展示了電子戰軟件中組件式定時器開發路徑。為更好服務于電子戰軟件開發,性能優良、反復測試組件的積極應用必須得到重視。