并行接口程序設(shè)計_第1頁
并行接口程序設(shè)計_第2頁
并行接口程序設(shè)計_第3頁
并行接口程序設(shè)計_第4頁
并行接口程序設(shè)計_第5頁
已閱讀5頁,還剩16頁未讀, 繼續(xù)免費閱讀

下載本文檔

版權(quán)說明:本文檔由用戶提供并上傳,收益歸屬內(nèi)容提供方,若內(nèi)容存在侵權(quán),請進行舉報或認領(lǐng)

文檔簡介

并行接口程序設(shè)計本章介紹在Windows2000/XP下的并行接口的程序設(shè)計方法,分析一下目前進行并行接口編程的方法,可以歸納為幾種:DLL直接I/O方式:應(yīng)用程序通過一個可以進行端口I/O訪問的DLL接口軟件實現(xiàn)對并行接口的訪問,即通過調(diào)用第三方DLL接口軟件中的I/O端口讀寫函數(shù)實現(xiàn)對并行口的寄存器的讀寫。這樣的軟件很多,像Winlo、Inpout32、TVicPort等;ActiveX控件直接I/O方式:通過一個提供ActiveX控件實現(xiàn)對端口的直接I/O訪問,一般控件的方式采用VB編程比較簡單。這樣的軟件包括Inpout32、TVicPort等;?并行接口專用接口軟件:使用這一類軟件對并行接口編程要比上2種方法簡單,有些軟件支持中斷。這樣的軟件如TVicLPTo自己編寫驅(qū)動程序:直接在VC++環(huán)境下通過Windows2000DDK或WindowsXPDDK編寫驅(qū)動程序,這是一種最靈活的方法,但編程的難度比較大。5.1實現(xiàn)直接I/O方式的軟件并行接口的編程在不同的操作系統(tǒng)下采取不同的方法,在DOS和Windows95之前的操作系統(tǒng)下,可以直接對端口進行讀寫,根據(jù)并行接口的不同模式的寄存器進行讀寫操作就可以完成各種模式的接口編程。在目前的Windows2000/XP操作系統(tǒng)下,不能直接對端口寄存器進行訪問,這是由于Windows2000/XP對系統(tǒng)底層操作采取了屏蔽的策略,對用戶而言,系統(tǒng)變得更為安全,但這卻給接口和接口軟件開發(fā)人員帶來了不小的困難,因為只要應(yīng)用程序中涉及到底層的操作,開發(fā)人員就不得不深入到Windows的內(nèi)核去編寫屬于系統(tǒng)級的設(shè)備驅(qū)動程序。對并行口的讀寫操作就是如此,由于Windows對系統(tǒng)的保護,應(yīng)用程序不允許直接I/O操作。在Windows2000/XP操作系統(tǒng)下,正規(guī)的接口程序的編程方法是采取驅(qū)動程序的開發(fā)方法。由于驅(qū)動程序需要與操作系統(tǒng)最底層進行交互,因此不同的操作系統(tǒng)的底層結(jié)構(gòu)對應(yīng)不同的設(shè)備驅(qū)動程序模型。Windows2000/XP與Windows9x的內(nèi)部結(jié)構(gòu)不同,這兩類操作系統(tǒng)的設(shè)備驅(qū)動程序是不兼容的,為了解決不同的操作系統(tǒng)的結(jié)構(gòu)的差異帶來的設(shè)備驅(qū)動程序的不兼容的問題,微軟公司在1997年提出了Windows操作系統(tǒng)的驅(qū)動程序模型,即WDM(WindowsDriverModel)oWDM設(shè)備驅(qū)動程序的開發(fā)是在VC++下通過DDK(DeviceDevelopmentKit:設(shè)備驅(qū)動程序開發(fā)包)才能完成的,這種方法的編程是比較復(fù)雜的,需要了解操作系統(tǒng)的內(nèi)部結(jié)構(gòu),并需要熟練的VC++開發(fā)經(jīng)驗。如果不采用WDM的方法,一個簡單實用的方法是使用間接的I/O方式,就是在應(yīng)用程序調(diào)用一個第三方提供的直接I/O接口程序,由這個間接的I/O程序模塊實現(xiàn)對端口的讀寫。下面介紹幾種這樣的軟件產(chǎn)品。Inpout32Inpout32:由LOGIX4U提供的免費軟件,可以在/網(wǎng)站下載。Inpout32提供了以DLL文件和AxtiveX的OCX文件兩形式提供了直接訪問I/O端口的函數(shù),在文件中只封裝了2個函數(shù),Inp32()和Out32()。支持從Windows95/98/Me到WindowsNT/2000/XP的多種操作系統(tǒng)。Inpout32只提供對I/O端口的訪問,不針對具體的接口類型,原則上可以完成所有面向寄存器訪問編程的應(yīng)用程序。但Inpout32沒有提供中斷的支持,所以只能完成以查詢控制方式的程序,不能實現(xiàn)中斷控制方式的程序設(shè)計。這可能會影響接口的傳輸速度,同時也使得軟件的CPU占用率很高。很可貴的是,在下載的軟件包中提供了DLL和OCX文件的VC++源程序代碼,這對于開發(fā)接口相關(guān)的DLL程序和OCX控件程序很有參考價值。TVicPortEnTech提供了用于接口編程的多個軟件產(chǎn)品,包括TVicTW32、TVicLPT和TVicPort等,這些軟件可以在EnTech的網(wǎng)站/dev/index.shtm上獲得,其中TVicPort是一個免費的軟件,是TVicHW32的簡化版。TVicPort是需要安裝的,默認的目錄是C:\TVicPortPersonal,在該目錄下有Docs和Samples兩個目錄,分別是說明文件和程序例子源文件。核心模塊被安裝到了系統(tǒng)目錄。TVicPort功能說明TVicPort的功能包括:?直接I/O訪問;-通過一個指針將物理存儲器影射用戶程序的存儲空間;-增強對并行接口的支持,可以直接控制和檢測并行端口的信號線;-提供獲得IDE硬盤的制造商信息的函數(shù),如硬盤序列號,可以實現(xiàn)軟件的硬盤邦定;?支持WindowsXP64bit。TVicPort提供的核心模塊文件包括TVicPort.sys、TVicPort.vxd、TVicPort.dll和TVicPort.ocx四個。其中TVicPort.vxd是用于Windows9x/ME的虛擬設(shè)備驅(qū)動程序,TVicPort.sys是用于Windows2000/XP的內(nèi)核模式驅(qū)動程序,DLL和OCX是應(yīng)用程序接口模塊,實現(xiàn)應(yīng)用程序與設(shè)備驅(qū)動程序的連接。雖然TVicPort支持多種語言平臺,但DLL函數(shù)更適合用于VC++編程,而OCX文件適合用于VB編程。TVicPort提供兩種對于端口的訪問方式,即“Hard”和“Soft”方式,其中“Soft”方式的讀寫速度比較快,但當被讀寫的端口地址被另一個內(nèi)核模式驅(qū)動程序占用時會訪問失效。而“Hard”方式可以避免這種情況,即使端口被另一個內(nèi)核模式驅(qū)動程序占用也能完成可靠的讀寫,但其訪問速度比“Soft”方式慢。函數(shù)默認的訪問方式是“Hard”方式,可以使用SetHardAccess()函數(shù)更改訪問方式。也可以通過函數(shù)TestHardAccess(涵數(shù)返回當前的訪問方式。TVicPort的DLL函數(shù)下面介紹TVicPort的DLL文件提供的VC++格式接口函數(shù)。這些函數(shù)的原形說明在TVicPort.h中,在VC++中加入TVicPort.h后可以直接按照下面介紹的格式實現(xiàn)調(diào)用。如果在VB中調(diào)用這些函數(shù),可以在VB工程中加入\Samples\VB\PortLib.bas模塊,在模塊中對全部函數(shù)作了聲明,可以參照模塊中的聲明細節(jié)實現(xiàn)在VB中的調(diào)用。TVicPort.dll提供的公共函數(shù)BOOLOpenTVicPort():打開(加載)TVicPort.vxd或TVicPort.sys設(shè)備驅(qū)動。參數(shù):無。返回:打開成功返回TRUE,失敗返回FALSE。BOOLIsDriverOpened():測試驅(qū)動程序是否打開。參數(shù):無。返回:驅(qū)動程序已打開返回TRUE,未打開返回FALSEovoidCloseTVicPort():關(guān)閉(卸載)設(shè)備驅(qū)動程序。voidSetHardAccess(BOOLHardAccess):設(shè)置當前的訪問方式為“Hard”或“Soft”參數(shù):TRUE表示設(shè)置為“Hard”方式,F(xiàn)ALSE表示設(shè)置為“Soft”方式。返回:無。BOOLTestHardAccess():測試當前的訪問方式。參數(shù):無。返回:TRUE表示“Hard”方式,F(xiàn)ALSE表示“Soft”方式。TVicPort.dll提供的端口訪問函數(shù)UCHARReadPort(USHORTPortAddr)讀端口1個字節(jié)。USHORTReadPortW(USHORTPortAddr)讀端口2個字節(jié)(字)。ULONGReadPortL(USHORTPortAddr):讀端口4個字節(jié)(雙字)。參數(shù):端口地址。返回:讀得的端口數(shù)據(jù)。voidWritePort(USHORTPortAddr,UCHARbData:寫1個字節(jié)到端口。voidWritePortW(USHORTPortAddr,USHORTwData)寫2個字(字)節(jié)到端口。voidWritePortL(USHORTPortAddr,ULONGlData:寫4個字節(jié)(雙字)到端口。參數(shù):PortAddr為端口地址,bData/wData/lData為要寫的數(shù)據(jù)。返回:無。voidReadPortFIFO(USHORTPortAddr,USHORTNumPorts,UCHAR*Buffer)voidReadPortWFIFO(USHORTPortAddr,USHORTNumPorts,USHORT*Buffer)voidReadPortLFIFO(USHORTPortAddr,USHORTNumPorts,ULONG*Buffer)功能:讀取多個單元(字節(jié)/字/雙字)到一個輸入緩沖區(qū)。參數(shù):PortAddr為端口地址,NumPorts為單元數(shù),Buffer為輸入緩沖區(qū)指針。voidWritePortFIFO(USHORTPortAddr,USHORTNumPorts,UCHAR*Buffer)voidWritePortWFIFO(USHORTPortAddr,USHORTNumPorts,USHORT*Buffer)voidWritePortLFIFO(USHORTPortAddr,USHORTNumPorts,ULONG*Buffer)功能:寫多個單元(字節(jié)/字/雙字)到端口。參數(shù):PortAddr為端口地址,NumPorts為單元數(shù),Buffer為輸出緩沖區(qū)指針。TVicPort.dll提供的存儲器訪問函數(shù)ULONGMapPhysToLinear(ULONGPhysAddr,ULONGMappedSize)功能:映射系統(tǒng)的物理存儲器空間到應(yīng)用程序的線性存儲空間。參數(shù):PhysAddr為32位物理存儲器起始地址,MappedSize為映射的字節(jié)數(shù)。返回:物理存儲器空間的首字節(jié)映射到線性存儲空間的地址。voidUnmapMemory(ULONGPhysAddr,ULONGMappedSize)功能:關(guān)閉由MapPhysToLinear(涵數(shù)建立的映射。參數(shù):PhysAddr為32位物理存儲器起始地址,MappedSize為映射的字節(jié)數(shù)。返回:無。UCHARGetMem(ULONGMappedAddress,ULONGMemOffset)USHORTGetMemW(ULONGMappedAddress,ULONGMemOffset)ULONGGetMemL(ULONGMappedAddress,ULONGMemOffset)功能:讀取線性存儲空間的字節(jié)/字/雙字數(shù)據(jù),以上3個函數(shù)可以用于VB,因為在VC++中可以直接通過指針實現(xiàn)線性地址空間的數(shù)據(jù)讀取,而VB缺乏指針的操作手段。參數(shù):MappedAddress為由MapPhysToLinear(涵數(shù)返回的線性存儲空間的首地址,MemOffset為線性存儲空間的偏移位置。返回:讀取的數(shù)據(jù)。voidSetMem(ULONGMappedAddress,ULONGMemOffset,UCHARbValue)voidSetMemW(ULONGMappedAddress,ULONGMemOffset,USHORTwValue)voidSetMemL(ULONGMappedAddress,ULONGMemOffset,ULONGdwValue)功能:向線性存儲空間寫入一個字節(jié)/字/雙字數(shù)據(jù),以上3個函數(shù)可以用于VB,因為在VC++中可以直接通過指針實現(xiàn)線性地址空間的數(shù)據(jù)讀取,而VB缺乏指針的操作手段。參數(shù):MappedAddress為由MapPhysToLinear(涵數(shù)返回的線性存儲空間的首地址,MemOffset為線性存儲空間的偏移位置,bValue/wValue/dwValue為要寫入的數(shù)據(jù)。返回:無。(4) TVicPort.dll提供的并行接口訪問函數(shù)UCHARGetLPTNumber():獲得當前的并行接口號。參數(shù):無返回:1為LPT1,2為LPT2...。voidSetLPTNumber(UCHARLptNumber):設(shè)置一個并行口為當前并行口。參數(shù):lptNumber為1表示LPT1,2表示LPT2...。返回:無。UCHARGetLPTNumPorts():檢測系統(tǒng)中的LPT數(shù)目。參數(shù):無。返回:系統(tǒng)中的LPT數(shù)目。ULONGGetLPTBasePort():獲得當前LPT的基地址。參數(shù):無。返回:當前LPT基地址。UCHARAddNewLPT(USHORTPortBaseAddress:添加一個LPT。參數(shù):PortBaseAddress為添加的LPT的基地址。返回:添加的LPT的號碼,同時設(shè)置添加的LPT為當前LPT。BOOLGetPin(UCHARPinNumber):讀取當前LPT連接器的可讀取線狀態(tài)。參數(shù):PinNumber為DB25連接器的線編號,1?25。返回:TRUE表示高電平,F(xiàn)ALSE表示低電平。voidSetPin(UCHARPinNumber,BOOLPinLevel)設(shè)置當前LPT的可寫線狀態(tài)。參數(shù):PinNumber為DB25連接器的線編號,PinLevel為TRUE表示高電平,F(xiàn)ALSE表示低電平。返回:無。BOOLGetLPTAckwl()獲得當前LPT的Acknowledge線狀態(tài)。參數(shù):無。返回:TRUE表示有效,F(xiàn)ALSE為無效狀態(tài)。BOOLGetLPTBusy():獲得當前LPT的Busy線狀態(tài)。參數(shù):無。返回:TRUE表示有效,F(xiàn)ALSE為無效狀態(tài)。BOOLGetLPTPaperEnd():獲得當前LPT的PaperEnd線狀態(tài)。參數(shù):無。返回:TRUE表示有效,F(xiàn)ALSE為無效狀態(tài)。BOOLGetLPTSlct():獲得當前LPT的Slct線狀態(tài)。參數(shù):無。返回:TRUE表示有效,F(xiàn)ALSE為無效狀態(tài)。BOOLGetLPTError():獲得當前LPT的Error線狀態(tài)。參數(shù):無。返回:TRUE表示有效,F(xiàn)ALSE為無效狀態(tài)。voidLPTInit():在當前LPT的Init線(DB25的16號引腳)輸出一個短暫的脈沖。參數(shù):無。返回:無。voidLPTSlctIn():設(shè)置當前LPT的SelectIn線為有效。參數(shù):無。返回:無。voidLPTStrobe():在當前LPT的Strobe線(DB25的1號引腳)輸出一個短暫的脈沖。參數(shù):無。返回:無。voidLPTAutofd(BOOLFlag):設(shè)置當前LPT的AutoLF線(DB25的14號引腳)狀態(tài)。參數(shù):Flag為TRUE表示有效,F(xiàn)LASE表示無效。返回:無。(5)TVicPort.dll提供的IDE硬盤訪問函數(shù)voidGetHDDInfo(UCHARIdeNumber,UCHARMaster,HDDInfo*Info)功能:返回IDE硬盤的制造商參數(shù)。參數(shù):IdeNumber為IDE通道號,Masker為1表示Masker設(shè)備,0表示Slave設(shè)備。*Info為指向一個HDDInfo結(jié)構(gòu)的指針,該函數(shù)填寫HDDInfo。返回:無。HDDInfo結(jié)構(gòu)如下:

typedefstruct_HDDInfo{ULONGBufferSize;〃緩沖存儲器容量ULONGDoubleTransfer;〃雙字節(jié)數(shù)據(jù)傳輸支持ULONGControllerType;〃控制器類型ULONGECCMode;//ECC校驗?zāi)J経LONGSectorsPerInterrupt;〃每中斷的扇區(qū)數(shù)ULONGCylinders;〃柱面數(shù)ULONGHeads;〃磁頭數(shù)ULONGSectorsPerTrack;〃每磁道扇區(qū)數(shù)charModel[41];〃型號charSerialNumber[21];〃序列號charRevision[9];}HDDInfo,*pHDDInfo;〃控制器版本號TVicPort的ActiveX控件TVicPort的ActiveX控件屬性和DLL函數(shù)接口基本功能是類似的,個別DLL函數(shù)在ActiveX控件沒有。ActiveX控件的接口方式更適合在VB中使用。當然并不是在VB中必須使用TVicPort的ActiveX控件方式,也可以采用DLL方式調(diào)用TVicPort.dll中的函數(shù)。首先在VB中創(chuàng)建一個StandardEXE類型的工程,選擇Project菜單中的Components菜單項,打開Components窗口,在Controls選項卡中找到TVicPortActiveXControlModele,選中后按確定按鈕將TVicPort控件插入到Toolbox中,在將其拖到應(yīng)用程序的窗體中,在窗體呈現(xiàn)一個TVP標記,然后就可以編寫代碼了。TVicPort的ActiveX屬性成員名稱和功能與DLL函數(shù)的有差別,全部的ActiveX屬性成員以及和DLL函數(shù)的對應(yīng)關(guān)系見下表。表5-1PVicPort的ActiveX屬性成員以及和DLL函數(shù)的對應(yīng)關(guān)系A(chǔ)ctiveX屬性成員對應(yīng)功能的DLL函數(shù)OpenDriverOpenTVicPortActiveHWIsDriverOpenedCloseDriverCloseTVicPortHardAccessSetHardAccess、TestHardAccessPortReadPort、WritePortPortWReadPortW、WritePortWPortLReadPortL、WritePortLMapPhysToLinearMapPhysToLinearUnmapMemoryUnmapMemoryMemGetMem、SetMemMemWGetMemW、SetMemWMemLGetMemL、SetMemLLPTNumberGetLPTNumber、SetLPTNumberLPTNumPortsGetLPTNumPortsLPTBasePortGetLPTBasePortPinGetPin、SetPinLPTAckwlGetLPTAckwlLPTBusyGetLPTBusyLPTPaperEndGetLPTPaperEndLPTSlctGetLPTSlctLPTErrorGetLPTErrorLPTInitLPTInitLPTSlctInLPTSlctInLPTStrobeLPTStrobeLPTAutofdLPTAutofdTVicLPTTVicLPT是EnTech提供的并行接口的專用接口軟件,該軟件包本身不是免費的,但公司網(wǎng)站上還提供了一個免費TVicLPT全功能評估版本??梢栽贓nTech的網(wǎng)站/dev/index.shtm上下載。TVicLPT是需要安裝的,TVicLPT1.3版默認的安裝目錄是C:\TVicLPT13,在該目錄下有Help目錄和各種語言的測試程序源代碼目錄。核心模塊TVicLPT.ocx和TVicLPT.sys被安裝到了系統(tǒng)目錄。TVicLPT功能說明TVicLPT1.3版只提供ActiveX控件文件,沒有提供DLL方式的函數(shù)調(diào)用接口。該控件支持多種語言調(diào)用,在安裝的目錄下可以找到VB、MSVC、BorlandC++Builder和BorlandDelphi的測試程序代碼。TVicLPT的功能包括:?檢測標準的地址上的并行端口;-具備添加非標準的并行口的能力;?檢測并行口支持的模式,包括SPP、PS/2、EPP和ECP等;-可以在不進行位操作的情況下實現(xiàn)并行口模式的轉(zhuǎn)換;?通過“名字”實現(xiàn)對并行口的直接訪問;-直接訪問和操作LPT的連接器上的信號;?實現(xiàn)硬件中斷的掛接。TVicLPT的ActiveX控件屬性成員下面以VB語法格式說明TVicLPT的ActiveX控件的屬性成員。(1) 公共的屬性和方法object.Active[=value]功能:打開/關(guān)閉設(shè)備驅(qū)動程序,或檢測設(shè)備驅(qū)動程序打開狀態(tài)。參數(shù):Value為設(shè)置參數(shù),1表示打開第一個驅(qū)動程序?qū)嵗?表示打開第二個驅(qū)動程序?qū)嵗?表示關(guān)閉驅(qū)動程序。返回:1表示成功打開驅(qū)動程序,0表示為打開或打開失敗。object.NumLPTs功能:檢測系統(tǒng)安裝的標準的LPT數(shù)目。參數(shù):無。返回:LPT數(shù)目。object.AddCustomPort(CustomBaseAddressAsInteger)功能:添加非標準的(無法通過NumLPTs檢測到的)LPT到系統(tǒng)。參數(shù):CustomBaseAddress為添加的LPT的基地址。返回:無。object.Acquired[=value]功能:鎖定當前的LPT以防止被其他應(yīng)用程序訪問,或檢測鎖定狀態(tài)。該屬性成員只用于Windows9x/ME。參數(shù):value為設(shè)定值,1表示鎖定,0表示為鎖定或解除鎖定。返回:可以是以下常數(shù)(在lptCVT.bas中定義)LPT_NOT_ACQUIRED:未鎖定;LPT_ACQUIRE_SUCCESS:鎖定成功;LPT_ACQUIRE_REFUSED:已經(jīng)被另一個應(yīng)用程序鎖定;LPT_ACQUIRE_BAD_PORT:LPT號錯誤或操作系統(tǒng)為Windows2000/XP;LPT_ACQUIRE_NOT_OPENED:設(shè)備驅(qū)動程序未打開。(2) 當前LPT和模式的屬性和方法object.CurrentLPT[=value]功能:設(shè)置或獲得當前LPT號。參數(shù):value為設(shè)定值,表示LPT號。返回:當前LPT號。object.CurrentLptMode[=value]功能:設(shè)置或獲得當前LPT的當前工作模式。參數(shù):value為設(shè)定值,表示模式,可以是以下常數(shù)(在lptCVT.bas中定義)LPT_SPP_MODE:SPP模式;LPT_PS2_MODE:PS/2模式;LPT_EPP_MODE:EPP模式;LPT_FAST_CENTRONIX:Centronix模式;LPT_ECP_MODE:ECP模式。返回:獲得的當前LPT的工作模式,值的定義同上。object.MaxLptMode功能:獲得當前LPT支持的“最大”工作模式。參數(shù):無。返回:“最大”工作模式值。可以是以下常數(shù)(在lptCVT.bas中定義)LPT_NOT_PRESENT=0LPT_SPP_MODE=1LPT_PS2_MODE=2LPT_EPP_MODE=3LPT_FAST_CENTRONIX=4LPT_ECP_MODE=5object.EPPEnabled功能:檢測當前的LPT是否支持EPP模式。參數(shù):無。返回:TRUE表示支持EPP,F(xiàn)ALSE表示不支持EPP模式。LPT寄存器相關(guān)的屬性和方法object.BasePortAddress功能:返回當前LPT的基地址。參數(shù):無。返回:當前LPT的基地址值。object.ReadMode[=value]功能:設(shè)置或返回當前LPT的數(shù)據(jù)寄存器的讀寫狀態(tài)。參數(shù):value為設(shè)定值,0表示“只寫”,1表示“只讀”。SPP不支持“只讀”。返回:TRUE表示“只讀”模式,F(xiàn)ALSE表示“只寫”模式。object.DataPort[=value]object.StatusPort[=value]object.ControlPort[=value]object.EcrPort[=value]object.CfgaPort[=value]object.CfgbPort[=value]object.FifoPort[=value]object.EPPAddressPort[=value]object.EPPDataPort[=value]功能:以上9個屬性成員用于從當前LPT不同的寄存器讀或向當前LPT不同的寄存器寫數(shù)據(jù)。它們針對的寄存器分別為數(shù)據(jù)寄存器、狀態(tài)寄存器、控制寄存器、ECR寄存器、CFGA寄存器、CFGB寄存器、FIFO寄存器、EPP地址寄存器和EPP數(shù)據(jù)寄存器。參數(shù):value為設(shè)定值,為寫到當前LPT的相應(yīng)寄存器的數(shù)據(jù)。返回:從當前LPT的相應(yīng)寄存器讀出的數(shù)據(jù)。LPT寄存器位相關(guān)的屬性和方法object.DataPortBit(BitNumberAsInteger)[=value]object.StatusPortBit(BitNumberAsInteger)[=value]object.ControlPortBit(BitNumberAsInteger)[=value]object.EcrPortBit(BitNumberAsInteger)[=value]object.CfgaPortBit(BitNumberAsInteger)[=value]object.CfgbPortBit(BitNumberAsInteger)[=value]功能:以上6個屬性用于設(shè)置或返回當前LPT的不同寄存器的指定位。6個不同屬性分別對應(yīng)數(shù)據(jù)寄存器、狀態(tài)寄存器、控制寄存器、ECR寄存器、CFGA和CFGB寄存器。參數(shù):BitNumber參數(shù)為位序號,0~7。value為設(shè)定值,0或1。返回:獲得的不同的寄存器的指定位的值,0或1。(5) LPT連接器位相關(guān)的屬性和方法object.Pin(PinNumberAsInteger][=value]功能:用于設(shè)置或返回當前LPT的DB25連接器上的指定線的信號狀態(tài)。當前LPT的讀寫狀態(tài)(由ReadMode屬性設(shè)定)將影響該屬性成員的執(zhí)行。參數(shù):PinNumber參數(shù)為連接器線序號,1~25。value為設(shè)定值,0或1。返回:獲得的線狀態(tài),TRUE為高電平,F(xiàn)ALSE為低電平。object.PulseStrobe(By^alDelayCyclesAsLong)功能:在當前LPT的Strobe線(DB25的1號引腳)輸出一個短暫的正脈沖。參數(shù):DelayCycles參數(shù)為一個和輸出脈沖寬度相關(guān)的相對時間間隔,如為0表示盡可能的短。返回:無。object.PulseStrobeAndWaitBus(TimeOutAsInteger)功能:在當前LPT的Strobe線(DB25的1號引腳)輸出一個短暫的正脈沖,但只有當外設(shè)送到接口的BUSY線信號變?yōu)橛行顟B(tài)才結(jié)束Strobe線的脈沖。參數(shù):TimeOut參數(shù)為一個相對的時間間隔表示等待BUSY信號的超時時間。返回:TRUE表示成功,未超時;FALSE表示超時。(6) 中斷相關(guān)的屬性和方法object.IrqNumber[=value]功能:設(shè)置和獲得當前LPT的中斷號。參數(shù):value是一個設(shè)定值,指定中斷號,取值范圍為1?15。通常LPT1使用中斷7,LPT2使用中斷5。返回:當前使用的中斷號。object.UnmaskIRQ功能:解除當前LPT中斷屏蔽,當硬件產(chǎn)生,將引發(fā)一個LptInterrupt事件。參數(shù):無。返回:無。object.MaskIRQ功能:屏蔽當前LPT中斷。參數(shù):無。返回:無。object.IrqCounter功能:獲得當前LPT發(fā)生的中斷數(shù)量。參數(shù):無。返回:中斷數(shù)。object_LptInterruptBjV^ZDataPortAsInteger,ByValStatusPortAsInteger,_ByValTimeStampLoAsLong,ByValTimeStampHiAsLong)功能:當LPT的硬件產(chǎn)生中斷時調(diào)用的函數(shù)。參數(shù):DataPort和StatusPort產(chǎn)生中斷時的數(shù)據(jù)寄存器和狀態(tài)寄存器,TimeStampLo和TimeStampHi分別為時間郵票的低半部分和高半部分,參見API函數(shù)QueryPerformanceCounter()。批量讀寫相關(guān)的方法object.ReadEppByteArrayfByValNumOfBytesAsLong,ByRefByteBufferAsAny)object.ReadEppWordArray(ByValNumOfWordsAsLong,ByRefWordBufferAsAny)object.ReadEppLongArray(ByValNumOfDWordsAsLong,ByRefLongBufferAsAny)功能:這三個函數(shù)使用在EPP模式,分別用于讀取字節(jié)、字和雙字型數(shù)組。參數(shù):NumOfBytes、NumOfWords和NumOfDWords分別為三個函數(shù)讀取的字節(jié)、字和雙字數(shù),ByteBuffer、WordBuffer和LongBuffer分別為三個函數(shù)的輸入數(shù)據(jù)緩沖區(qū)。object.WriteEppByteArray(ByValNumOfBytesAsLong,ByRefByteBufferAsAny)object.WriteEppWordArray(ByValNumOfWordsAsLong,ByRefWordBufferAsAny)object.WriteEppLongArray(ByValNumOfDWordsAsLong,ByRefLongBufferAsAny)功能:這三個函數(shù)使用在EPP模式,分別用于向LPT寫字節(jié)、字和雙字型數(shù)組。參數(shù):NumOfBytes、NumOfWords和NumOfDWords分別為三個函數(shù)要寫入的字節(jié)、字和雙字數(shù),ByteBuffer、WordBuffer和LongBuffer分別為三個函數(shù)的輸出數(shù)據(jù)緩沖區(qū)。5.2一個PC對等連接的并行接口測試實驗進行并行接口實驗的簡單方法是將兩臺pc通過一條并行接口電纜連接起來,可以通過軟件測試并行接口的一些特性。本節(jié)介紹一個這樣的并行接口實驗。5.2.1對等連接工作模式在對等連接中,并行接口必須工作在可以雙向傳輸?shù)哪J剑诂F(xiàn)有的IEEE-1284標準中,PS/2、EPP和ECP支持字節(jié)雙向傳輸。在這三種模式中,PS/2和ECP模式比較適合對等連接。在PS/2模式中,握手信號可以自由的收程序的控制,本實驗選擇PS/2模式。連接電纜由于并行接口最初的設(shè)計是針對打印機的,盡管在后續(xù)的升級中增加了多種模式,但有一點是沒有改變的,就是并行接口的設(shè)計是用于連接主機與外設(shè)的,如果使用并行接口連接兩臺主機,實現(xiàn)對等連接,可能要對接口信號線的功能作一些調(diào)整,設(shè)計一個合理的連接方案是遇到的第一個問題。在并行接口的信號線中,有8條雙向數(shù)據(jù)線D0?D7,8條地線,4條控制輸出線和5條狀態(tài)輸入線。通過連接電纜將兩端PC并行口的數(shù)據(jù)線和地線對應(yīng)引腳連接,再將一端的4條控制輸出線與另一端的5條狀態(tài)輸入線中的4條連接。下面的連接中可考慮到了ECP

模式的信號連接關(guān)系。表5-2并行接口的ECP模式PC-PC連接電纜A端計卜算機接口線中間連接B端計算機接口線信號名寄存器位線號線號寄存器位信號名nStrobeC01>>10S6nAck數(shù)據(jù)線D02[1k]2D0數(shù)據(jù)線D13[1k]3D1D24[1k]4D2D35[1k]5D3D46[1k]6D4D57[1k]7D5D68[1k]8D6D79[1k]9D7nAckS610<<1C0nStrobeBusyS711<<14C1nAutoFdPErrorS512<<16C2nInitnAutoFdC114>>11S7BusySelectS413<<17C3nSelectInnInitC216>>12S5PErrornSelectInC317>>13S4SelectGround18..2518..25Ground電纜的連接關(guān)系如下圖。

圖5-1ECP的PC-PC連接器關(guān)系5.2.2軟件設(shè)計測試程序在VB下設(shè)計,并行接口的操作通過TVicLPT控件實現(xiàn)。1.測試程序的功能測試程序是為了測試并行接口在PS/2模式的功能,主要實現(xiàn)以下功能:?可以完成對控制寄存器的位操所,通過對控制寄存器的位操作實現(xiàn)對接口信號線的狀態(tài)控制;?可以實時檢測信號線的狀態(tài),這是通過讀狀態(tài)寄存器實現(xiàn)的。需要在定時器的控制下讀取狀態(tài)寄存器;-可以實現(xiàn)對數(shù)據(jù)寄存器的讀寫;?可以檢測中斷的產(chǎn)生;?可以實現(xiàn)字符傳輸。2.程序定時的實現(xiàn)雖然在程序中使用了Timer控件,但是不能使用該控件完成超時控制,Timer控件定時器完成超時控制會出現(xiàn)以下問題:-VB中的Timer控件產(chǎn)生的時間間隔的精度很低,它的硬件時鐘的更新頻率為每秒約18次,不能完成高精度的定時要求;在程序上,如果采用查詢控制方式,接收程序代碼部分實際上是在狀態(tài)查詢定時器的事件觸發(fā)下執(zhí)行的,這樣在接收數(shù)據(jù)的過程中就無法使用狀態(tài)查詢定時器完成計時。本程序中使用一個系統(tǒng)定時器,通過API函數(shù)獲得定時器的當前值,相關(guān)的API函數(shù)為QueryPerformanceCounter和QueryPerformanceFrequency,分別用于獲得系統(tǒng)定時器的計數(shù)值和技術(shù)頻率。需要在VB程序中對這兩個API函數(shù)聲明,用以下代碼聲明。DeclareFunctionQueryPerformanceCounterLib"Kernel32”(XAsCurrency)AsBooleanDeclareFunctionQueryPerformanceFrequencyLib"Kernel32”(XAsCurrency)AsBoolean在讀數(shù)據(jù)、寫數(shù)據(jù)和等待一個狀態(tài)時都可以在開始時刻調(diào)用QueryPerformanceCounter函數(shù)獲得開始的時刻,在操作過程中再調(diào)用該函數(shù)獲得當前的時間,用以下公式計算時間:(當前時刻一開始時刻)『定時器頻率在程序中可以使用以下語句獲得系統(tǒng)定時器頻率SysCountFrequency:Result=QueryPerformanceFrequency(SysCountFrequency)在需要記憶時間的位置插入以下語句可以獲得當時的系統(tǒng)定時器常數(shù)SysCount:Result=QueryPerformanceCounter(SysCount)程序使用的控件說明程序使用VB實現(xiàn)。首先建立一個StandardEXE工程,將TVicLPTActiveXControlModule加入到VB的Form中,默認名稱是TVicLPTl。程序中添加的全部控件見下表。表5-3并行接口對等連接測試程序使用的控件控件名稱控件類型功能說明TVicLPTlTVicLPT訪問接口的控件frmModeFrame包含optPS2Mode和optECPMode的容器optPS2ModeOptionButton選擇PS/2模式optECPModeOptionButton選擇ECP模式frmlnterruptFrame包含中斷和傳送的控件容器chkInterruptCheckBox控制中斷使能lblAckIntLabel中斷計時器,計數(shù)由nAck產(chǎn)生的中斷txtDataTrsTextBox傳送的數(shù)據(jù)字節(jié)值,發(fā)送后程序控制加1txtDataRcvTextBox接收到的數(shù)據(jù)字節(jié)值cmdTransCommandButton數(shù)據(jù)字節(jié)發(fā)送按鈕chkReadyCheckBox用于設(shè)定接收就緒狀態(tài)cmdReadDataCommandButton讀取數(shù)據(jù)寄存器

cmdWriteDataCommandButton寫數(shù)據(jù)寄存器txtDataTextBox數(shù)據(jù)寄存器的讀寫數(shù)據(jù)lblDataLabel數(shù)據(jù)寄存器的讀寫數(shù)據(jù)的十六進制和二進制cmdRegisterCommandButton讀取控制寄存器和狀態(tài)寄存器按鈕chkAutoRegisterCheckBox自動讀取控制寄存器和狀態(tài)寄存器使能cmdControl()CommandButton陣列,用于改變狀態(tài)寄存器的位lblStatus()Label陣列,用于顯示狀態(tài)寄存器的位Timer1Timer自動讀取控制和狀態(tài)寄存器的定時器程序界面程序設(shè)計界面如下。圖5-2并行接口對等連接測試程序界面程序運行后,如果并行接口支持PS/2模式,LPTMode容器中的PS/2選中。右下方的6個按鈕對應(yīng)控制寄存器的C0?C5位,可以通過按鈕分別控制對應(yīng)位的值,C0?C4分別對應(yīng)接口的1(nStrobe)、14(nAutoFd)、16(nInit)和17(nSelectIn)引腳,C4為IRQEnable,中斷使能控制,C5位是方向控制位。狀態(tài)寄存器的S2?S7位有定義,S2(IRQ)為中斷狀態(tài)位,S3?S7為接口引腳15(nFault)、13(Select)、12(PError)、10(nAck)和11(Busy)的狀態(tài)。當AutoRegisiter選中,狀態(tài)位顯示的更新通過定時器自動完成,否則需要通過Regisiter按鈕手動更新顯示。ReadData和WriteData按鈕分別用于讀、寫數(shù)據(jù)寄存器。下方顯示數(shù)據(jù)寄存器的數(shù)值。TransData容器用于控制中斷和數(shù)據(jù)傳輸,發(fā)送方按TransData按鈕可以發(fā)送數(shù)據(jù)到對方,接收方需要選中ReadyReceive,使得接收PC機處于接收就緒狀態(tài)。在數(shù)據(jù)傳送過程中,發(fā)送方?jīng)]發(fā)送一個字節(jié),發(fā)送數(shù)據(jù)字節(jié)值自動加1。接收方可以觀察中斷計數(shù)值InterruptCount確認中斷的產(chǎn)生,以及接收數(shù)據(jù)值確認傳輸?shù)恼_性。程序代碼全程變量DimSRAsByte,CRAsByte,ECRAsByteDimResultAsBooleanDimSysCountFrequencyAsCurrency,SysCount1AsCurrency,SysCount2AsCurrency選擇定時器控制自動更新寄存器,打開、關(guān)閉定時器PrivateSubchkAutoregister_Click()IfchkAutoRegister.Value=0ThenTimer1.Enabled=FalseElseTimer1.Enabled=TrueEndIfEndSub選擇打開、關(guān)閉中斷PrivateSubchkInterrupt_Click()IfchkInterrupt.Value=0ThenTVicLPT1.MaskIrqElseTVicLPT1.UnmaskIrqEndIfEndSub設(shè)定、取消接收就緒PrivateSubchkReady_Click()IfchkReady.Value=1ThenTVicLPT1.ControlPortBit(0)=0TVicLPT1.ControlPortBit(1)=1TVicLPT1.ControlPortBit(5)=1chkInterrupt.Value=1TVicLPT1.UnmaskIrqTimer1.Enabled=FalsechkAutoRegister.Value=0ElsechkInterrupt.Value=0TVicLPTl.MaskIrqTimerl.Enabled=TruechkAutoRegister.Value=1EndIfEndSub讀取控制和狀態(tài)寄存器內(nèi)容PrivateSubcmdregister_Click()Timer1_TimerEndSub傳輸字節(jié)到對方計算機PrivateSubcmdTrans_Click()IfTVicLPT1.StatusPortBit(7)=0ThenExitSubTVicLPT1.ControlPortBit(5)=0TVicLPT1.DataPort=Val(txtDataTrs.Text)TVicLPT1.ControlPortBit(0)=1TVicLPT1.ControlPortBit(0)=0IfWaitStatus(100,7,1)ThenTVicLPT1.ControlPortBit(1)=0IfWaitStatus(100,7,0)ThentxtDataTrs.Text=IIf(Val(txtDataTrs.Text)=255,"0”,Str(Val(txtDataTrs.Text)+1))EndIfTVicLPT1.ControlPortBit(1)=1EndIfTVicLPT1.ControlPortBit(5)=1EndSub中斷處理,讀取數(shù)據(jù)并完成握手PrivateSubTVicLPT1_LptInterrupt(ByValDataValueAsInteger,ByValStatusValueAsInteger,_ByValLoTimeStampAsLong,ByValHiTimeStampAsLong)IfTVicLPT1.StatusPortBit(6)=1ThentxtDataRcv.Text=TVicLPT1.DataPortTVicLPT1.ControlPortBit(1)=0txtACKInt.Text=Str(Val(txtACKInt.Text)+1)IfWaitStatus(100,7,0)ThenTVicLPT1.ControlPortBit(1)=1TVicLPT1.ControlPortBit(1)=1EndIfEndSub延時或等待狀態(tài)寄存器特定位的變化,SValue為0、1之外的其他數(shù)為延時功能TimeOut:延時或等待時間(ms),SNo:狀態(tài)寄存器位序,SValue:期待的變化值PrivateFunctionWaitStatus(TimeOutAsSingle,SNoAsByte,SValueAsByte)DimdelayAsSingleWaitStatus=TrueResult=QueryPerformanceCounter(SysCount1)DoResult=QueryPerformanceCounter(SysCount2)delay=(SysCount2-SysCount1)/SysCountFrequency*1000'msLoopWhiledelay<TimeOutAndTVicLPT1.StatusPortBit(SNo)<>SValueIfdelay>=TimeOutThenWaitStatus=FalseEndFunction操作控制寄存器,Index為控制寄存器位序PrivateSubcmdControl_Click(IndexAsInteger)IfcmdControl(Index).Caption="0"ThencmdCont

溫馨提示

  • 1. 本站所有資源如無特殊說明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請下載最新的WinRAR軟件解壓。
  • 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請聯(lián)系上傳者。文件的所有權(quán)益歸上傳用戶所有。
  • 3. 本站RAR壓縮包中若帶圖紙,網(wǎng)頁內(nèi)容里面會有圖紙預(yù)覽,若沒有圖紙預(yù)覽就沒有圖紙。
  • 4. 未經(jīng)權(quán)益所有人同意不得將文件中的內(nèi)容挪作商業(yè)或盈利用途。
  • 5. 人人文庫網(wǎng)僅提供信息存儲空間,僅對用戶上傳內(nèi)容的表現(xiàn)方式做保護處理,對用戶上傳分享的文檔內(nèi)容本身不做任何修改或編輯,并不能對任何下載內(nèi)容負責(zé)。
  • 6. 下載文件中如有侵權(quán)或不適當內(nèi)容,請與我們聯(lián)系,我們立即糾正。
  • 7. 本站不保證下載資源的準確性、安全性和完整性, 同時也不承擔用戶因使用這些下載資源對自己和他人造成任何形式的傷害或損失。

最新文檔

評論

0/150

提交評論