畢業(yè)設(shè)計(jì)(論文)-基于Visual C的P2P文件傳輸系統(tǒng)的設(shè)計(jì)與實(shí)現(xiàn)_第1頁
畢業(yè)設(shè)計(jì)(論文)-基于Visual C的P2P文件傳輸系統(tǒng)的設(shè)計(jì)與實(shí)現(xiàn)_第2頁
畢業(yè)設(shè)計(jì)(論文)-基于Visual C的P2P文件傳輸系統(tǒng)的設(shè)計(jì)與實(shí)現(xiàn)_第3頁
畢業(yè)設(shè)計(jì)(論文)-基于Visual C的P2P文件傳輸系統(tǒng)的設(shè)計(jì)與實(shí)現(xiàn)_第4頁
畢業(yè)設(shè)計(jì)(論文)-基于Visual C的P2P文件傳輸系統(tǒng)的設(shè)計(jì)與實(shí)現(xiàn)_第5頁
已閱讀5頁,還剩39頁未讀 繼續(xù)免費(fèi)閱讀

下載本文檔

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

文檔簡(jiǎn)介

畢業(yè)設(shè)計(jì)報(bào)告(論文)題目:基于VisualC++的P2P文件傳輸系統(tǒng)的設(shè)計(jì)與實(shí)現(xiàn)所屬系計(jì)算機(jī)系_專業(yè)計(jì)算機(jī)科學(xué)與技術(shù)學(xué)號(hào)姓名指導(dǎo)教師起訖日期2021.22021.5設(shè)計(jì)地點(diǎn)南京網(wǎng)博_______東南大學(xué)成賢學(xué)院畢業(yè)設(shè)計(jì)報(bào)告〔論文〕誠(chéng)信承諾本人承諾所呈交的畢業(yè)設(shè)計(jì)報(bào)告〔論文〕及取得的成果是在導(dǎo)師指導(dǎo)下完成,引用他人成果的局部均已列出參考文獻(xiàn)。如論文涉及任何知識(shí)產(chǎn)權(quán)糾紛,本人將承當(dāng)一切責(zé)任。學(xué)生簽名:日期:P2P摘要P2P是peer-to-peer的縮寫,或稱為對(duì)等聯(lián)網(wǎng)。P2P技術(shù)使得網(wǎng)絡(luò)上的溝通變得容易,網(wǎng)絡(luò)上現(xiàn)有的許多效勞可以歸入P2P的行列。即時(shí)訊息系統(tǒng)如微軟的MSNMessenger及國(guó)內(nèi)的OICQ是最流行的P2P應(yīng)用。由于它們都需要有位于中心的效勞器來協(xié)調(diào),于是便有了編寫本軟件的設(shè)想。本軟件功能擺脫了中心效勞器的束縛,是一個(gè)實(shí)用性通信軟件。它的根本功能就是讓用戶能夠在局域網(wǎng)甚至在廣域網(wǎng)上點(diǎn)對(duì)點(diǎn)的進(jìn)行交流。由于TCP/IP連接協(xié)議的效勞是設(shè)計(jì)客戶端/效勞器應(yīng)用程序時(shí)的主流標(biāo)準(zhǔn),所以本軟件主要采用TCP/IP協(xié)議的網(wǎng)絡(luò)通信技術(shù);客戶端,效勞器類是從CAsyncSocket類中繼承來的,因此本軟件通信完全是異步的;程序在WindowsXP系統(tǒng)、VisualC++6.0下編譯通過,并在WindowsNT100M以太網(wǎng)上運(yùn)行良好。本軟件創(chuàng)立的是對(duì)話框應(yīng)用程序,采用多線程操作;連接后效勞器可以充當(dāng)客戶機(jī),客戶機(jī)也可以充當(dāng)效勞器。它們可以在同一臺(tái)計(jì)算機(jī)上,也可以把應(yīng)用程序復(fù)制到另一臺(tái)計(jì)算機(jī)上,這樣沒有中間效勞器存在,在兩個(gè)獨(dú)立的計(jì)算機(jī)上分別運(yùn)行應(yīng)用程序,從而通過網(wǎng)絡(luò)傳遞消息。本軟件主要完成了以下功能:根本文字聊天功能,傳輸文件功能,遠(yuǎn)程控制功能。還有語音聊天功能需要進(jìn)一步改良,才能到達(dá)預(yù)期效果。在傳輸文件過程中,需要建立另一個(gè)進(jìn)程,在新建的進(jìn)程中傳輸文件,并且可以隨時(shí)中斷傳輸;遠(yuǎn)程控制功能主要是獲取對(duì)方機(jī)器信息,獲取對(duì)方進(jìn)程,鎖定和解鎖鍵盤,鎖定和解鎖鼠標(biāo)等關(guān)鍵詞P2P;客戶端;效勞器;通信;多線程

P2PAbstractP2Pistheacronymforpeer-to-peer,orcalledonothernetwork.P2Pnetworktechnologymakesthecommunicationeasier,andmanyexistingservicescanbeclassifiedasP2Pservice.InstantmessagingsystemssuchasMicrosoft'sMSNMessengeranddomesticOICQwasthemostpopularP2Papplication.Astheybothneedthecentralservertocoordinatetheserver,thereisthepreparationofthissoftwareconcept.Thissoftwareisapracticalcommunicationsoftware,asitfunctionsfromacentralserverconstrains.ItsbasicfunctionistoallowuserstotheLANorWANintheonlinepeer-to-peerexchange.AsTCP/IPagreementlinkingtheserviceisdesignedclient/serverapplicationproceduresforthemainstreamstandards,Therefore,thesoftwareusedmainlyTCP/IPagreementnetworkcommunicationtechnology;client,serverfromCAsyncSocketinheritedcategory,andthereforethesoftwareiscompletelyasynchronouscommuni-cation;proceduresinWindowsXPsystemandunderVisualC++6.0compiler,andisrunninggoodinWindowsNTand100MEthernet.Thissoftwarecreatesthedialogboxapplicationsthroughmulti-threadedoperation;afterconnectiontheservercanactasclient,Clientscanalsoactasservers.Theycanbeonthesamecomputer,canalsocopytheapplicationtoanothercomputer,bydoingsointermediateservernolongerexists.operatingapplicationsseparatelyintwocomputerssothatinformationisimpartedthroughthenetwork.Thesoftwarecompletedthefollowingmajorfunctions:basictextchat,filetransferfunctions,remotecontrolfunctions.Voicechatalsoneedtobefurtherimprovedinordertoachievethedesiredeffect.Transferfilesintheprocess,weneedtocreateanotherprocessinthenewprocesstotransferfiles,andtransmissioncanbeinterruptedatanytime;Remotecontrolfunctionisthemainaccesstoothermachinesofinformation,accesstoeachother'sprocess,lockandunlockthekeyboardandmouselockingandunlockingother.KeywordsP2P;client;Server;communication;multi-thread目錄第一章緒論 11.1課題的主要內(nèi)容和國(guó)內(nèi)外開展方向 11.2軟件的預(yù)期實(shí)現(xiàn)的目標(biāo)和完成狀況 2效勞器端的應(yīng)用程序?qū)⑼瓿扇缦鹿δ?2客戶端的通訊程序?qū)⑼瓿扇缦鹿δ?31.2.3目前的實(shí)現(xiàn)狀況 3第二章通信方案的設(shè)計(jì) 42.1TCP與UDP協(xié)議的選擇 42.1.1TCP協(xié)議 42.1.2UDP協(xié)議 52.2多線程編程 52.3WinInet編程與WinSock編程的比擬及其優(yōu)點(diǎn) 62.4通信原理及過程 6第三章具體的設(shè)計(jì)方法 83.1根本的SOCKET函數(shù) 83.2通信過程 113.2.1C/S模式的請(qǐng)求響應(yīng)方式 113.2.2SOCKET建立連接過程 12傳輸文件過程 13遠(yuǎn)程控制過程 143.3具體實(shí)現(xiàn)局部 15實(shí)現(xiàn)根本聊天的功能 15實(shí)現(xiàn)傳輸文件的功能 22截圖 24語音通信 25遠(yuǎn)程控制 27第四章存在的問題及解決方法 31第五章后記 34第六章參考文獻(xiàn) 35第七章致謝 36第一章緒論1.1課題的主要內(nèi)容和國(guó)內(nèi)外開展方向 P2P可以理解為“伙伴對(duì)伙伴〞的意思。目前人們認(rèn)為其在加強(qiáng)網(wǎng)絡(luò)上人的交流、文件交換、分布計(jì)算等方面大有前途。2002年,尼古拉斯·曾斯特姆(NiklasZennstrom)把P2P音樂下載軟件KaZaA買給一家小公司時(shí),得到了50萬美元;2005年,他把P2P通信軟件Skype出售給eBay時(shí),賺到了21億美金。三年前,因?yàn)镻2P音樂下載,他和創(chuàng)業(yè)伙伴面臨著來自美國(guó)唱片工業(yè)協(xié)會(huì)的訴訟威脅;三年后,P2P支撐的互聯(lián)網(wǎng)通信已經(jīng)成為市場(chǎng)的寵兒。 P2P使得一個(gè)用戶可以直接連接到其它用戶的計(jì)算機(jī),并交換文件,而不是像過去那樣連接到效勞器去瀏覽與下載。P2P另一個(gè)重要特點(diǎn)是改變互聯(lián)網(wǎng)現(xiàn)在的以大網(wǎng)站為中心的狀態(tài),重返“非中心化〞,并把權(quán)力交還給用戶。 P2P看起來似乎很新,但是正如B2C、B2B是將現(xiàn)實(shí)世界中很平常的東西移植到互聯(lián)網(wǎng)上一樣,P2P并不是什么新東西。在現(xiàn)實(shí)生活中我們每天都按照P2P模式面對(duì)面地或者通過交流和溝通。即使從網(wǎng)絡(luò)看,P2P也不是新概念,P2P是互聯(lián)網(wǎng)整體架構(gòu)的根底?;ヂ?lián)網(wǎng)最根本的協(xié)議TCP/IP并沒有客戶端和效勞器的概念,所有的設(shè)備都是通訊的平等的一端。在十年之前,所有的互聯(lián)網(wǎng)上的系統(tǒng)都同時(shí)具有效勞器和客戶端的功能。當(dāng)然,后來開展的那些架構(gòu)在TCP/IP之上的軟件確實(shí)采用了客戶機(jī)/效勞器的結(jié)構(gòu):瀏覽器和Web效勞器,郵件客戶端和郵件效勞器。但是,對(duì)于效勞器來說,它們之間仍然是對(duì)等聯(lián)網(wǎng)的。以email為例,互聯(lián)網(wǎng)上并沒有一個(gè)巨大的、唯一的郵件效勞器來處理所有的email,而是對(duì)等聯(lián)網(wǎng)的郵件效勞器相互協(xié)作把email傳送到相應(yīng)的效勞器上去。但是過去的5年里,互聯(lián)網(wǎng)的開展至少?gòu)耐獗砩线h(yuǎn)離了P2P今天,P2P再一次被關(guān)注主要是由于Napster以及ICQ類軟件的出現(xiàn),雖然在Napster之前P2P方式的研究也從未停止。Napster正是喚醒了深藏在互聯(lián)網(wǎng)背后的對(duì)等聯(lián)網(wǎng)。Napster的文件共享功能在局域網(wǎng)中共享目錄也是再平常不過的事情。但是Napster的成功促使人們認(rèn)識(shí)到把這種“對(duì)等聯(lián)網(wǎng)〞拓展到整個(gè)互聯(lián)網(wǎng)范圍的可能性。當(dāng)然,在許多人的眼中,Napster并不是純粹的P2P,它仍然需要一個(gè)處于中心協(xié)調(diào)機(jī)制。P2P引導(dǎo)網(wǎng)絡(luò)計(jì)算模式從集中式向分布式偏移,也就是說網(wǎng)絡(luò)應(yīng)用的核心從中央效勞器向網(wǎng)絡(luò)邊緣的終端設(shè)備擴(kuò)散:效勞器到效勞器、效勞器到PC機(jī)、PC機(jī)到PC機(jī),PC機(jī)到WAP……所有網(wǎng)絡(luò)節(jié)點(diǎn)上的設(shè)備都可以建立P2P對(duì)話。這使人們?cè)贗nternet上的共享行為被提到了一個(gè)更高的層次,使人們以更主動(dòng)深刻的方式參與到網(wǎng)絡(luò)中去,正如I2(第二代互聯(lián)網(wǎng):簡(jiǎn)單的說,就是借助IPv6的力量,解決絕大多數(shù)第一代互聯(lián)網(wǎng)遇到的難題,把網(wǎng)絡(luò)、電視、還有所有可能想象到的應(yīng)用囊括其中)之父Doug.VanHouweling在他的中國(guó)之行時(shí)說到的:“下一代互聯(lián)網(wǎng)民們將真正參與到網(wǎng)絡(luò)中來,每個(gè)人都能為網(wǎng)絡(luò)的資源和功能擴(kuò)展作出自己的奉獻(xiàn)。〞P2P給互聯(lián)網(wǎng)的分布、共享精神帶來了無限的遐想。在國(guó)外,P2P開展已經(jīng)如火如荼,Intel、Sun、Microsoft等公司已經(jīng)在制定P2P的標(biāo)準(zhǔn)。P2P技術(shù)的巨大影響力橫亙了內(nèi)容發(fā)行、通信等領(lǐng)域,它廣闊的前景引來微軟、Google、雅虎、新聞集團(tuán)等公司的關(guān)注,但是P2P對(duì)內(nèi)容產(chǎn)業(yè)以及對(duì)傳統(tǒng)通信公司的負(fù)面影響依然存在,在很多國(guó)家都曾經(jīng)出現(xiàn)過互聯(lián)網(wǎng)效勞提供商封殺P2P的事件。Napster雖然敗訴,這似乎預(yù)示著P2P的挫折,但實(shí)際上這卻意味著由P2P帶來的新的規(guī)那么正在建立,相關(guān)的數(shù)字版權(quán)立法已經(jīng)開始,P2P的力量開始逐步顯示出來。

國(guó)內(nèi)P2P的市場(chǎng)根本從2000年底開始逐步啟動(dòng)。目前,國(guó)內(nèi)P2P的應(yīng)用主要有兩個(gè)方向:文件共享及協(xié)同工作。具有代表性的技術(shù)有:P2P多線程斷點(diǎn)續(xù)傳的實(shí)現(xiàn);P2P之UDP穿透NAT的原理與實(shí)現(xiàn);IPTV業(yè)務(wù)承載網(wǎng)的解決;IPTV流媒體分發(fā)和交付技術(shù)的新突破;第三代google排名搜索引擎技術(shù);網(wǎng)格的應(yīng)用;基于P2P思想的QQ蠕蟲的原理與防治;網(wǎng)絡(luò);流媒體應(yīng)用等。1.2軟件的預(yù)期實(shí)現(xiàn)的目標(biāo)和完成狀況效勞器端的應(yīng)用程序?qū)⑼瓿扇缦鹿δ堋ㄟ^數(shù)據(jù)庫(kù)驗(yàn)證用戶名密碼登陸——設(shè)置效勞器的賬號(hào)——監(jiān)聽客戶端的連接請(qǐng)求——為請(qǐng)求連接的客戶端建立SOCKET隊(duì)列——向客戶端發(fā)送消息——從客戶端接收消息——向客戶端發(fā)送文件——從客戶端接收文件——與客戶端語音通信——截取屏幕——可以與客戶端進(jìn)行遠(yuǎn)程協(xié)助〔控制鍵盤鼠標(biāo)進(jìn)程〕客戶端的通訊程序?qū)⑼瓿扇缦鹿δ堋ㄟ^數(shù)據(jù)庫(kù)驗(yàn)證用戶名密碼登陸——建立與效勞器的連接——關(guān)閉與效勞器的連接——向效勞器發(fā)送消息——從效勞器接收消息——向效勞器發(fā)送文件——從效勞器接收文件——與效勞器語音通信——截取屏幕——可以與效勞器進(jìn)行遠(yuǎn)程協(xié)助〔控制鍵盤鼠標(biāo)進(jìn)程〕目前的實(shí)現(xiàn)狀況由于這套軟件采用VisualC++進(jìn)行網(wǎng)絡(luò)編程,同時(shí)還涉及到了數(shù)據(jù)庫(kù)編程和VC++的多線程,為了使用戶接口美觀、使用方便,還需要采用編程的方法進(jìn)行處理和美化,另外處理網(wǎng)絡(luò)通信和用戶信息交流還要建立各種輔助的數(shù)據(jù)結(jié)構(gòu)和信息管理系統(tǒng),所以需要處理的細(xì)節(jié)問題較多;此外,效勞器和客戶端軟件要分別編寫,這樣還牽扯到它們之間通信方案的制定,這樣造成整套軟件的編碼工作量較大,所以整個(gè)軟件的實(shí)現(xiàn)目標(biāo)并未完全實(shí)現(xiàn),主要是與數(shù)據(jù)庫(kù)連接,語音聊天和界面的美工尚未完成。第二章通信方案的設(shè)計(jì)2.1TCP與UDP協(xié)議的選擇TCP協(xié)議TCP/IP通常指的是關(guān)于TCP和IP的任何東西,它是一個(gè)統(tǒng)稱,它既可以包括其它協(xié)議,其它應(yīng)用程序,還可以包括網(wǎng)絡(luò)介質(zhì)。根本結(jié)構(gòu)如圖2.1,這個(gè)結(jié)構(gòu)存在于Internet中計(jì)算機(jī)之中,它決定了計(jì)算機(jī)在網(wǎng)絡(luò)上的動(dòng)作。TELNETTELNETFTPSMTPDNSTCPUDPIPARPANETSATNETLAN協(xié)議網(wǎng)絡(luò)應(yīng)用層傳輸層網(wǎng)絡(luò)層物理層和數(shù)鏈層圖2SEQ圖2\*ARABIC1TCP/IP模型中早期的協(xié)議和網(wǎng)絡(luò) 如果IP數(shù)據(jù)包中有已經(jīng)封好的TCP數(shù)據(jù)包,那么IP將把它們向‘上’傳送到TCP層。TCP將包排序并進(jìn)行錯(cuò)誤檢查,同時(shí)實(shí)現(xiàn)虛電路間的連接。TCP資料包中包括序號(hào)和確認(rèn),所以未按照順序收到的包可以被排序,而損壞的包可以被重傳。TCP將它的信息送到更高層的應(yīng)用程序,例如Telnet的效勞程序和客戶程序。應(yīng)用程序輪流將信息送回TCP層,TCP層便將它們向下傳送到IP層,設(shè)備驅(qū)動(dòng)程序和物理介質(zhì),最后到接收方。面向連接的效勞〔例如Telnet、FTP、rlogin、XWindows和SMTP〕需要高度的可靠性,所以它們使用了TCP。DNS在某些情況下使用TCP協(xié)議發(fā)送和接收域名數(shù)據(jù)庫(kù),但使用UDP協(xié)議傳送有關(guān)單個(gè)主機(jī)的信息。TCP協(xié)議即采用流式套接字SOCKET_STREAM。UDP協(xié)議UDP與TCP位于同一層,UDP不被應(yīng)用于那些使用虛電路的面向連接的效勞,UDP主要用于那些面向查詢應(yīng)答的效勞,例如NFS。相對(duì)于FTP或Telnet,這些效勞需要交換的信息量較小。使用UDP的效勞包括NTP〔網(wǎng)落時(shí)間協(xié)議〕和DNS〔DNS也使用TCP〕。欺騙UDP包比欺騙TCP包更容易,因?yàn)閁DP沒有建立初始化連接〔也可以稱為握手〕〔因?yàn)樵趦蓚€(gè)系統(tǒng)間沒有虛電路〕,也就是說,與UDP相關(guān)的效勞面臨著更大的危險(xiǎn)。UDP協(xié)議使用數(shù)據(jù)報(bào)式套接字SOCKET_DGRAM。雖然基于TCP/IP連接協(xié)議〔流套接字〕的效勞是設(shè)計(jì)客戶機(jī)/效勞器應(yīng)用程序時(shí)的主流標(biāo)準(zhǔn),但有些效勞也是可以通過無連接協(xié)議〔資料報(bào)套接字〕提供的。先介紹一下TCPsocket與UDPsocket在傳送數(shù)據(jù)時(shí)的特性:Stream(TCP)Socket提供雙向、可靠、有次序、不重復(fù)的數(shù)據(jù)傳送。Datagram(UDP)Socket雖然提供雙向的通信,但沒有可靠、有次序、不重復(fù)的保證,所以UDP傳送數(shù)據(jù)可能會(huì)收到無次序、重復(fù)的數(shù)據(jù),甚至數(shù)據(jù)在傳輸過程中出現(xiàn)遺漏。由于UDPSocket在傳送數(shù)據(jù)時(shí),并不保證數(shù)據(jù)能完整地送達(dá)對(duì)方,所以本程序采用TCP協(xié)議處理Socket,以保證數(shù)據(jù)的正確性。一般情況下TCPSocket的數(shù)據(jù)發(fā)送和接收是調(diào)用send()及recv()這兩個(gè)函數(shù)來達(dá)成,而UDPSocket那么是用sendto()及recvfrom()這兩個(gè)函數(shù),這兩個(gè)函數(shù)調(diào)用成功發(fā)揮發(fā)送或接收的數(shù)據(jù)的長(zhǎng)度,否那么返回SOCKET_ERROR。2.2多線程編程由于用到對(duì)話框,所以單線程的操作會(huì)嚴(yán)重影響程序功能的實(shí)現(xiàn),所以采用多線程操作,使得在翻開一個(gè)對(duì)話框時(shí),不會(huì)影響到另一個(gè)對(duì)話框的功能,在MFC程序中創(chuàng)立一個(gè)線程,調(diào)用AfxBeginThread函數(shù):CWinThreadAfxBeginThread(AFX_THREADPROCpfnThreadProc,控制函數(shù)LPVOIDpParam,傳遞給控制函數(shù)的參數(shù)intnPriority=THREAD_PRIORITY_NORMAL,線程的優(yōu)先級(jí)UINTnStackSize=0,線程的堆棧大小DWORDdwCreateFlags=0,線程的創(chuàng)立標(biāo)志LPSECURITY_ATTRIBUTESlpSecurityAttrs=NULL線程的平安屬性);結(jié)束進(jìn)程:進(jìn)程只是提供了一段地址空間和內(nèi)核對(duì)象,其運(yùn)行是通過在其地址空間內(nèi)的主線程來表達(dá)的。當(dāng)主線程的進(jìn)入點(diǎn)函數(shù)返回時(shí),進(jìn)程也就隨之結(jié)束。這種進(jìn)程的終止方式是進(jìn)程的正常退出,進(jìn)程中的所有線程資源都能夠得到正確的去除。除了這種進(jìn)程的正常退出方式外,有時(shí)還需要在程序中通過代碼來強(qiáng)制結(jié)束本進(jìn)程或其它進(jìn)程的運(yùn)行。Exit-Process〔〕函數(shù)即可在進(jìn)程中的某個(gè)線程中使用,并將立即終止本進(jìn)程的運(yùn)行。該函數(shù)具有強(qiáng)制性,在執(zhí)行完畢后進(jìn)程即已經(jīng)被結(jié)束,因此位于其后的任何代碼將不能被執(zhí)行。雖然ExitProcess〔〕函數(shù)可以在結(jié)束進(jìn)程的同時(shí)通知與其相關(guān)聯(lián)的動(dòng)態(tài)鏈接庫(kù),但是由于它的這種執(zhí)行的強(qiáng)制性,使得ExitProcess〔〕函數(shù)在使用上將存在平安隱患。2.3WinInet編程與WinSock編程的比擬及其優(yōu)點(diǎn) 1、網(wǎng)絡(luò)編程簡(jiǎn)單使用WinSock編程,用戶需要熟悉網(wǎng)絡(luò)通信及TCP/IP和各種協(xié)議;而使用WinInet進(jìn)行開發(fā),就不需要了解具體實(shí)現(xiàn)協(xié)議,從而簡(jiǎn)化了網(wǎng)絡(luò)編程。另外,WinInet函數(shù)的調(diào)用形式與多數(shù)Win32API函數(shù)類似,也便于用戶掌握和使用。 2、程序維護(hù)簡(jiǎn)單,升級(jí)方便 Internet開展迅速,其各種協(xié)議也在不斷開展與完善。WinInet隱藏了協(xié)議的具體的協(xié)議細(xì)節(jié),使得應(yīng)用程序不必直接實(shí)現(xiàn)協(xié)議,而只需要調(diào)用一個(gè)協(xié)議接口,這樣在協(xié)議更新時(shí),只要更新WinInet動(dòng)態(tài)鏈接庫(kù)即可,程序本身無須做任何修改。 3、性能優(yōu)越,支持多線程WinInet函數(shù)支持多線程,可以在多線程中調(diào)用各種WinInet函數(shù)而不用擔(dān)憂發(fā)生各種并發(fā)問題,WinInet函數(shù)在內(nèi)部處理所有的多線程并發(fā)、死鎖等問題。2.4通信原理及過程 大多數(shù)通過網(wǎng)絡(luò)進(jìn)行通信的應(yīng)用程序,不管是通過因特網(wǎng)還是小型的辦公網(wǎng)絡(luò),它們都使用同樣的原那么和功能來執(zhí)行通信。計(jì)算機(jī)上的一個(gè)應(yīng)用程序正在等待另一個(gè)程序翻開通信連接,可以說這前一個(gè)應(yīng)用程序正在“偵聽〞該連接請(qǐng)求,這很像你在等待某人給你打時(shí),一直在留心鈴聲。與時(shí)同時(shí),另一個(gè)應(yīng)用程序,一般是運(yùn)行在另一臺(tái)計(jì)算機(jī)上〔當(dāng)然也可以是同一臺(tái)機(jī)器上〕,試圖同第一個(gè)應(yīng)用程序連接。這種試圖找開連接的方式就類似于向某人打。你撥了號(hào)碼,并希望要找的那個(gè)人正在線的另一頭等接。當(dāng)然,要完成的呼叫,必須知道被呼叫方的號(hào)碼。同樣的道理,試圖連接到第一個(gè)應(yīng)用程序的這個(gè)程序也必須知道第一個(gè)應(yīng)用程序的網(wǎng)絡(luò)位置或網(wǎng)絡(luò)地址。一旦兩個(gè)應(yīng)用程序建立了連接,它們之間就可以互相發(fā)送和接收消息。正像兩個(gè)人打交談一樣,這個(gè)連接是一個(gè)雙向的通道,即雙方都可以發(fā)送消息。最后,如果一方或雙方完成了對(duì)話,連接即關(guān)閉,就像打完一樣,你能夠知道中的對(duì)方是否把給掛斷了,或者雙方由于其它原因連接不上了。一旦該應(yīng)用程序同一個(gè)應(yīng)用程序之間建立了連接,就能夠在它的對(duì)話框里鍵入要發(fā)送的文本消息,并把它們發(fā)送給另一個(gè)應(yīng)用程序。消息被發(fā)送之后,就被加到已發(fā)送消息的列表中。接收到的每一條消息都被復(fù)制到所有已收到的消息列表中。這樣就能看到完整的已發(fā)送和已接收到的消息列表,還可以對(duì)發(fā)送消息的應(yīng)用程序和接收消息的應(yīng)用程序進(jìn)行比擬。這就是在兩個(gè)或多個(gè)應(yīng)用程序間進(jìn)行網(wǎng)絡(luò)通信的根本工作原理。第三章具體的設(shè)計(jì)方法3.1根本的SOCKET函數(shù)為了方便這種Client/Server模型的網(wǎng)絡(luò)編程,90年代初,由Microsoft聯(lián)合了其它幾家公司共同制定了一套WINDOWS下的網(wǎng)絡(luò)編程接口,即WindowsSockets標(biāo)準(zhǔn),它不是一種網(wǎng)絡(luò)協(xié)議,而是一套開放的、支持多種協(xié)議的Windows下的網(wǎng)絡(luò)編程接口?,F(xiàn)在的Winsock已經(jīng)根本上實(shí)現(xiàn)了與協(xié)議無關(guān),你可以使用Winsock來調(diào)用多種協(xié)議的功能,但較常使用的是TCPIP協(xié)議。Socket實(shí)際在計(jì)算機(jī)中提供了一個(gè)通信端口,可以通過這個(gè)端口與任何一個(gè)具有Socket接口的計(jì)算機(jī)通信。應(yīng)用程序在網(wǎng)絡(luò)上傳輸,接收的信息都通過這個(gè)Socket接口來實(shí)現(xiàn)。1.在初始化階段調(diào)用WSAStartup()此函數(shù)在應(yīng)用程序中初始化WindowsSocketsDLL,只有此函數(shù)調(diào)用成功后,應(yīng)用程序才可以再調(diào)用其它WindowsSocketsDLL中的API函數(shù)。在程序中調(diào)用該函數(shù)的形式如下:WSAStartup((WORD)((181),〔LPWSADATA〕&WSAData),其中(181)表示我們用的是WinSocket1.1版本,WSAata用來存儲(chǔ)系統(tǒng)傳回的關(guān)于WinSocket的資料。2、建立Socket初始化WinSock的動(dòng)態(tài)連接庫(kù)后,需要在效勞器端建立一個(gè)監(jiān)聽的Socket,為此可以調(diào)用Socket()函數(shù)用來建立這個(gè)監(jiān)聽的Socket,并定義此Socket所使用的通信協(xié)議。此函數(shù)調(diào)用成功返回Socket對(duì)象,失敗那么返回INVALID_SOCKET(調(diào)用WSAGetLastError()可得知原因,所有WinSocket的API函數(shù)都可以使用這個(gè)函數(shù)來獲取失敗的原因)。SOCKETPASCALFARsocket(intaf,inttype,intprotocol)參數(shù)af目前只提供PF_INET(AF_INET);type:Socket的類型(SOCK_STREAM、SOCK_DGRAM);protocol:通訊協(xié)定(如果使用者不指定那么設(shè)為0);如果要建立的是遵從TCPIP協(xié)議的socket,第二個(gè)參數(shù)type應(yīng)為SOCK_STREAM,如為UDP〔數(shù)據(jù)報(bào)〕的socket,應(yīng)為SOCK_DGRAM。3、綁定端口接下來要為效勞器端定義的這個(gè)監(jiān)聽的Socket指定一個(gè)地址及端口〔Port〕,這樣客戶端才知道待會(huì)要連接哪一個(gè)地址的哪個(gè)端口,為此我們要調(diào)用bind()函數(shù),該函數(shù)調(diào)用成功返回0,否那么返回SOCKET_ERROR。intPASCALFARbind(SOCKETs,conststructsockaddrFARname,intnamelen);參數(shù):s:Socket對(duì)象名;name:Socket的地址值,這個(gè)地址必須是執(zhí)行這個(gè)程序所在機(jī)器的IP地址;namelen:name的長(zhǎng)度;如果使用者不在意地址或端口的值,那么可以設(shè)定地址為INADDR_ANY,及Port為0,WindowsSockets會(huì)自動(dòng)將其設(shè)定適當(dāng)之地址及Port(1024到5000之間的值)。此后可以調(diào)用getsockname()函數(shù)來獲知其被設(shè)定的值。4、監(jiān)聽當(dāng)效勞器端的Socket對(duì)象綁定完成之后,效勞器端必須建立一個(gè)監(jiān)聽的隊(duì)列來接收客戶端的連接請(qǐng)求。listen()函數(shù)使效勞器端的Socket進(jìn)入監(jiān)聽狀態(tài),并設(shè)定可以建立的最大連接數(shù)(目前最大值限制為5,最小值為1)。該函數(shù)調(diào)用成功返回0,否那么返回SOCKET_ERROR。intPASCALFARlisten(SOCKETs,intbacklog);參數(shù):s:需要建立監(jiān)聽的Socket;backlog:最大連接個(gè)數(shù);效勞器端的Socket調(diào)用完listen〔〕后,如果此時(shí)客戶端調(diào)用connect〔〕函數(shù)提出連接申請(qǐng)的話,Server端必須再調(diào)用accept()函數(shù),這樣效勞器端和客戶端才算正式完成通信程序的連接動(dòng)作。為了知道什么時(shí)候客戶端提出連接要求,從而效勞器端的Socket在恰當(dāng)?shù)臅r(shí)候調(diào)用accept()函數(shù)完成連接的建立,我們就要使用WSAAsyncSelect〔〕函數(shù),讓系統(tǒng)主動(dòng)來通知我們有客戶端提出連接請(qǐng)求了。該函數(shù)調(diào)用成功返回0,否那么返回SOCKET_ERROR。intPASCALFARWSAAsyncSelect(SOCKETs,HWNDhWnd,unsignedintwMsg,longlEvent);參數(shù):s:Socket對(duì)象;hWnd:接收消息的窗口句柄;wMsg:傳給窗口的消息;lEvent:被注冊(cè)的網(wǎng)絡(luò)事件,也即是應(yīng)用程序向窗口發(fā)送消息的網(wǎng)路事件,該值為以下值FD_READ、FD_WRITE、FD_OOB、FD_ACCEPT、FD_CONNECT、FD_CLOSE的組合,各個(gè)值的具體含意為FD_READ:希望在套接字S收到數(shù)據(jù)時(shí)收到消息;FD_WRITE:希望在套接字S上可以發(fā)送數(shù)據(jù)時(shí)收到消息;FD_ACCEPT:希望在套接字S上收到連接請(qǐng)求時(shí)收到消息;FD_CONNECT:希望在套接字S上連接成功時(shí)收到消息;FD_CLOSE:希望在套接字S上連接關(guān)閉時(shí)收到消息;FD_OOB:希望在套接字S上收到帶外數(shù)據(jù)時(shí)收到消息。具體應(yīng)用時(shí),wMsg應(yīng)是在應(yīng)用程序中定義的消息名稱,而消息結(jié)構(gòu)中的lParam那么為以上各種網(wǎng)絡(luò)事件名稱。5、效勞器端接受客戶端的連接請(qǐng)求當(dāng)Client提出連接請(qǐng)求時(shí),Server端窗會(huì)收到WinsockStack送來我們自定義的一個(gè)消息,這時(shí),我們可以分析lParam,然后調(diào)用相關(guān)的函數(shù)來處理此事件。為了使效勞器端接受客戶端的連接請(qǐng)求,就要使用accept()函數(shù),該函數(shù)新建一Socket與客戶端的Socket相通,原先監(jiān)聽之Socket繼續(xù)進(jìn)入監(jiān)聽狀態(tài),等待他人的連接要求。該函數(shù)調(diào)用成功返回一個(gè)新產(chǎn)生的Socket對(duì)象,否那么返回INVALID_SOCKET。SOCKETPASCALFARaccept(SCOKETs,structsockaddrFARaddr,intFARaddrlen);參數(shù):s:Socket的識(shí)別碼;addr:存放來連接的客戶端的地址;addrlen:addr的長(zhǎng)度。6、結(jié)束socket連接結(jié)束效勞器和客戶端的通信連接是很簡(jiǎn)單的,這一過程可以由效勞器或客戶機(jī)的任一端啟動(dòng),只要調(diào)用closesocket()就可以了,而要關(guān)閉Server端監(jiān)聽狀態(tài)的socket,同樣也是利用此函數(shù)。另外,與程序啟動(dòng)時(shí)調(diào)用WSAStartup()憨數(shù)相對(duì)應(yīng),程序結(jié)束前,需要調(diào)用WSACleanup()來通知WinsockDll釋放Socket所占用的資源。這兩個(gè)函數(shù)都是調(diào)用成功返回0,否那么返回SOCKET_ERROR。intPASCALFARclosesocket(SOCKETs);參數(shù):s:Socket的識(shí)別碼;intPASCALFARWSACleanup(void);7、建立客戶端的Socket客戶端應(yīng)用程序首先也是調(diào)用WSAStartup()函數(shù)來與Winsock的動(dòng)態(tài)連接庫(kù)建立關(guān)系,然后同樣調(diào)用socket()來建立一個(gè)TCP或UDPsocket〔相同協(xié)定的sockets才能相通,TCP對(duì)TCP,UDP對(duì)UDP〕。與效勞器端的socket不同的是,客戶端的socket可以調(diào)用bind()函數(shù),由自己來指定IP地址及port號(hào)碼;但是也可以不調(diào)用bind(),而由Winsock來自動(dòng)設(shè)定IP地址及port號(hào)碼。8、客戶端提出連接申請(qǐng)客戶端的Socket使用connect()函數(shù)來提出與效勞器端的Socket建立連接的申請(qǐng),函數(shù)調(diào)用成功返回0,否那么返回SOCKET_ERROR。intPASCALFARconnect(SOCKETs,conststructsockaddrFAR*name,intnamelen);參數(shù):s:Socket的識(shí)別碼;name:Socket想要連接的對(duì)方地址;namelen:name的長(zhǎng)度。9、數(shù)據(jù)的傳送以保證資料的正確性,一般情況下TCPSocket的數(shù)據(jù)發(fā)送和接收是調(diào)用send()及recv()這兩個(gè)函數(shù)來達(dá)成,而UDPSocket那么是用sendto()及recvfrom()這兩個(gè)函數(shù),這兩個(gè)函數(shù)調(diào)用成功發(fā)揮發(fā)送或接收的資料的長(zhǎng)度,否那么返回SOCKET_ERROR。intPASCALFARsend(SOCKETs,constcharFAR*buf,intlen,intflags);參數(shù):s:Socket的識(shí)別碼buf:存放要傳送的資料的暫存區(qū);lenbuf:的長(zhǎng)度;flags:此函數(shù)被調(diào)用的方式。intPASCALFARrecv(SOCKETs,charFAR*buf,intlen,intflags);參數(shù):s:Socket的識(shí)別碼;buf:存放接收到的資料的暫存區(qū);lenbuf:的長(zhǎng)度flags:此函數(shù)被調(diào)用的方式。對(duì)StreamSocket言,我們可以接收到目前inputbuffer內(nèi)有效的資料,但其數(shù)量不超過len的大小。3.2通信過程3.2.1C/S模式的請(qǐng)求響應(yīng)方式圖3.SEQ圖3.\*ARABIC1TCP/IP協(xié)議三次握手過程在TCP/IP協(xié)議中,TCP協(xié)議提供可靠的連接效勞,采用三次握手建立一個(gè)連接〔如圖3.1〕。第一次握手:建立連接時(shí),客戶端發(fā)送syn包(syn=j)到效勞器,并進(jìn)入SYN_SEND狀態(tài),等待效勞器確認(rèn);第二次握手:效勞器收到syn包,必須確認(rèn)客戶的SYN〔ack=j+1〕,同時(shí)自己也發(fā)送一個(gè)SYN包〔syn=k〕,即SYN+ACK包,此時(shí)效勞器進(jìn)入SYN_RECV狀態(tài);第三次握手:客戶端收到效勞器的SYN+ACK包,向效勞器發(fā)送確認(rèn)包ACK(ack=k+1),此包發(fā)送完畢,客戶端和效勞器進(jìn)入ESTABLISHED狀態(tài),完成三次握手。完成三次握手,客戶端與效勞器開始傳送數(shù)據(jù)。SOCKET建立連接過程效勞器效勞器 客戶端create(),建立套接字band(),與本地地址綁定listen(),準(zhǔn)備好接受連接accept(),等待接受客戶端連接,receive()接收數(shù)據(jù)Close(),關(guān)閉套接字send(),發(fā)送數(shù)據(jù)Create(),建立套接字Connect(IP),與效勞器連接receive()接收數(shù)據(jù)Close(),關(guān)閉套接字send()發(fā)送數(shù)據(jù)圖3.SEQ圖3.\*ARABIC2SOCKET建立連接過程效勞器創(chuàng)立套接字后,進(jìn)行偵聽,客戶端創(chuàng)立套接字后進(jìn)行連接,一旦建立連接,就可以發(fā)送接收數(shù)據(jù),直到關(guān)閉套接字。傳輸文件過程自己中斷自己中斷效勞器客戶端向客戶端發(fā)送傳輸文件請(qǐng)求,等待等待效勞器的請(qǐng)求自己中斷開始傳輸文件進(jìn)程進(jìn)程開始傳輸文件進(jìn)程進(jìn)程SOCKET建立連接并傳輸文件SOCKET建立連接并傳輸文件過程中斷或?qū)Ψ降闹袛噙^程中斷或?qū)Ψ降闹袛鄠鬏斖戤?,結(jié)束進(jìn)程傳輸完畢,結(jié)束進(jìn)程關(guān)閉連接,返回關(guān)閉連接,返回對(duì)方拒絕對(duì)方拒絕圖3.SEQ圖3.\*ARABIC3傳輸文件過程首先效勞器向客戶端發(fā)送請(qǐng)求,要求傳送文件,在得到客戶端相應(yīng)之前,雙方都可以取消這次傳輸,同時(shí)通知對(duì)方已經(jīng)取消連接;一旦客戶端給了效勞器響應(yīng),那么建立進(jìn)程,進(jìn)行傳輸;建立的進(jìn)程里,要定義新的SOCKET套接字,以建立連接,在傳輸過程中,同樣可以進(jìn)行中斷,同時(shí)通知對(duì)方已經(jīng)取消連接;傳輸結(jié)束后,斷開連接,結(jié)束該進(jìn)程。遠(yuǎn)程控制過程客戶端效勞器已經(jīng)建立了連接客戶端效勞器已經(jīng)建立了連接已經(jīng)建立了連接發(fā)送遠(yuǎn)程控制請(qǐng)求接受遠(yuǎn)程控制請(qǐng)求修改注冊(cè)表向?qū)Ψ桨l(fā)送結(jié)果接受結(jié)果信息判斷命令類別退出退出圖3.SEQ圖3.\*ARABIC4遠(yuǎn)程控制過程首先客戶端向效勞器發(fā)出請(qǐng)求,效勞器同意后建立連接,用戶如果想執(zhí)行某個(gè)功能,那么向效勞器發(fā)送消息,效勞器收到消息后根據(jù)標(biāo)志字符判斷屬于哪項(xiàng)操作,然后作出相應(yīng)操作,直到退出。3.3具體實(shí)現(xiàn)局部實(shí)現(xiàn)根本聊天的功能 1、創(chuàng)立應(yīng)用程序創(chuàng)立一個(gè)對(duì)話框風(fēng)格的應(yīng)用程序,過程:設(shè)置工程名稱和保存路徑->選擇“根本對(duì)話框〞->選擇“WindowsSockets[W]〞->選擇“WindowsSockets[W]〞->選擇“作為靜態(tài)的DLL〞或“作為共享DLL〞->完成。具體過程如以下圖所示:①新建-〉工程-〉MFCAppWizard[exe],設(shè)置工程名稱和保存路徑〔如圖3.5〕:圖3.SEQ圖3.\*ARABIC5設(shè)置工程名稱和保存路徑②下一步選擇“根本對(duì)話框〞,點(diǎn)擊下一步〔圖3.6〕:圖3.SEQ圖3.\*ARABIC6選擇“根本對(duì)話框〞③選擇WindowsSockets[W],點(diǎn)擊下一步〔圖3.7〕:圖3.SEQ圖3.\*ARABIC7選擇“WindowsSockets[W]〞④如果想在其它機(jī)器上脫離函數(shù)庫(kù)運(yùn)行,選擇“作為靜態(tài)的DLL〞,否那么默認(rèn)的“作為共享DLL〞就行,點(diǎn)擊完成〔如圖3.8〕:圖3.SEQ圖3.\*ARABIC8選擇“作為靜態(tài)的DLL〞或“作為共享DLL〞 2、布置窗口和啟動(dòng)功能 對(duì)話框布局: ①客戶端登陸窗口(如圖3.9):圖3.SEQ圖3.\*ARABIC9客戶端登陸窗口 ②客戶端操作界面〔圖3.10〕:圖3.SEQ圖3.\*ARABIC10客戶端操作界面客戶端對(duì)話框上控件的作用如表3.1??丶δ躀D標(biāo)題VALUEBUTTON1連接到效勞器IDC_BUTTON1CONNECTBUTTON2停止與效勞器連接IDC_BUTTON2STOPBUTTON3發(fā)送消息IDC_BUTTON3SENDBUTTON4托盤〔縮放到右下角〕IDC_BUTTON4HIDEBUTTON5接收文件IDC_BUTTON5RECEIVEBUTTON6停止接受文件IDC_BUTTON6StopBUTTON7發(fā)送文件IDC_BUTTON7TransmissonBUTTON8語音聊天IDC_BUTTON8PHONEBUTTON10設(shè)置字體大小IDC_BUTTON10FONTBUTTON11去除編輯框內(nèi)紀(jì)錄IDC_BUTTON11clearPROGRESS1發(fā)送文件進(jìn)度IDC_PROGRESS1m_CtrlProgressSendLIST1顯示消息IDC_LIST1m_ctrMesssageEDIT2編輯要發(fā)送的消息IDC_EDIT2m_strMess表3.1客戶端對(duì)話框上控件的作用 ③效勞器登陸窗口〔如圖3.11〕:圖3.SEQ圖3.\*ARABIC11效勞器登陸窗口 ④效勞器操作界面〔如圖3.12〕:圖3.SEQ圖3.\*ARABIC12效勞器操作界面 效勞器對(duì)話框上控件的功能如表3.2??丶δ躀D標(biāo)題VALUEBUTTON1翻開效勞器IDC_BUTTON1SERVERBUTTON2停止與客戶端連接IDC_BUTTON2STOPBUTTON3發(fā)送消息IDC_BUTTON3SENDBUTTON4語音聊天IDC_BUTTON4PHONEBUTTON5更改用戶權(quán)限IDC_BUTTON5CHANGEBUTTON6發(fā)送文件IDC_BUTTON6TransmissonBUTTON7停止接受文件IDC_BUTTON7StopBUTTON8接收文件IDC_BUTTON8ReceiveBUTTON9設(shè)置字體IDC_BUTTON9FONTBUTTON10截圖IDC_BUTTON10CaptureBUTTON11托盤IDC_BUTTON11HIDEPROGRESS1發(fā)送文件進(jìn)度IDC_PROGRESS1m_CtrlProgressSendLIST1顯示消息IDC_LIST1m_ctlRecvdEDIT2編輯要發(fā)送的消息IDC_EDIT2m_strMsgSTATIC顯示連接狀態(tài)IDC_STATICSTATUSSTATIC2先是客戶端IPIDC_STATIC2m_socketIP表3.2效勞器對(duì)話框上控件的功能 3、創(chuàng)立客戶端和效勞器端創(chuàng)立的這兩個(gè)類基類為CasyncSocket,類名為MySocket,向該類中添加一個(gè)成員變量,用作指向父對(duì)話框窗口的指針。指定變量類型為Cdialog*,變量名為m_pWnd。還需要向該類中添加一個(gè)能設(shè)置指標(biāo)的方法,因此添加一個(gè)成員函數(shù)。指定類型為void,函數(shù)聲明為SetParent(CDialog*pWnd)。對(duì)于這個(gè)報(bào)路類還要做的是添加事件函數(shù),要參加的事件函數(shù)為: ①客戶端: voidOnConnect(intnErrorCode); virtualvoidOnReceive(intnErrorCode); ②效勞器: virtualvoidOnClose(intnErrorCode); virtualvoidOnReceive(intnErrorCode); virtualvoidOnAccept(intnErrorCode);添加了所有的函數(shù)后,應(yīng)向?qū)υ捒蝾愄砑右粋€(gè)報(bào)路類的變量,對(duì)于效勞器的功能,在對(duì)話框類中需要兩個(gè)變量,一個(gè)用于偵聽連接請(qǐng)求,另一個(gè)用于被連接到另一個(gè)應(yīng)用程序。變量名為m_ListenSocket和m_ConnectSocket。 4、連接應(yīng)用程序客戶端與效勞器的連接通過建立SOCKET套接字完成的,客戶端進(jìn)行連接,效勞器進(jìn)程偵聽,如果在規(guī)定的時(shí)間內(nèi)連接不上,或是網(wǎng)絡(luò)問題,那么系統(tǒng)自動(dòng)退出,提示用戶有錯(cuò)誤發(fā)生;一旦建立連接,就可以通過以定義函數(shù)發(fā)送和接受消息,直到用戶退出。具體操作如下:客戶端:首先獲取效勞器的IP地址,輸入后,點(diǎn)擊CONNECT按鈕,連接成功前不允許其它按鈕能夠工作,所以都設(shè)置位FALSE,例如:GetDlgItem(IDC_BUTTON1)->EnableWindow(FALSE)設(shè)置按鈕BUTTON1不能工作,由于對(duì)話框類CSocketDlg繼承了CAsyncSocket類,消息響應(yīng)函數(shù)里直接調(diào)用類成員Create(),Connect()即可,當(dāng)連接到效勞器后,自動(dòng)調(diào)用OnConnect〔〕,使對(duì)話框上各控件可以工作。效勞器端:類似于客戶端,點(diǎn)擊SERVER按鈕,連接成功前不允許其它按鈕能夠工作,所以都設(shè)置位FALSE,由于對(duì)話框類CMySeverDlg繼承了CAsyncSocket類,消息響應(yīng)函數(shù)里直接調(diào)用類成員Create(),Listen()即可,其中調(diào)用Create()時(shí)需要制定端口〔端口是一種抽象的軟件結(jié)構(gòu),包括一些數(shù)據(jù)結(jié)構(gòu)和IO緩沖區(qū)。應(yīng)用程序即進(jìn)程通過系統(tǒng)調(diào)用與某端口建立連接(binding)后,傳輸層傳給該端口的數(shù)據(jù)都被相應(yīng)的進(jìn)程所接收,相應(yīng)進(jìn)程發(fā)給傳輸層的數(shù)據(jù)都從該端口輸出。在TCP/IP協(xié)議的實(shí)現(xiàn)中,端口操作類似于一般的I/O操作,進(jìn)程獲取一個(gè)端口,相當(dāng)于獲取本地唯一的I/O文件,可以用一般的讀寫原語訪問〕,客戶連接時(shí)也是通過這個(gè)指定的端口;當(dāng)效勞器偵聽到客戶端的連接后,自動(dòng)調(diào)用OnAccept〔〕函數(shù),表示已經(jīng)和客戶端去的連接,使對(duì)話框上各控件可以工作;同時(shí)定義局部變量CStringCip和UINTCPort,調(diào)用庫(kù)函數(shù)GetPeerName〔〕得到客戶端IP和端口,并且能夠在STATIC2上顯示,GetDlgItem(IDC_STATIC2)->SetWindowText(Cip)。 5、發(fā)送與接收消息 這里有必要講解一下阻塞套接字與非阻塞套接字。阻塞套接字是指執(zhí)行此套接字的網(wǎng)絡(luò)調(diào)用時(shí),直到成功才返回,否那么一直阻塞在此網(wǎng)絡(luò)調(diào)用上,比方調(diào)用receive()函數(shù)讀取網(wǎng)絡(luò)緩沖區(qū)中的數(shù)據(jù),如果沒有數(shù)據(jù)到達(dá),將一直掛在receive()這個(gè)函數(shù)調(diào)用上,直到讀到一些數(shù)據(jù),此函數(shù)調(diào)用才返回;而非阻塞套接字是指執(zhí)行此套接字的網(wǎng)絡(luò)調(diào)用時(shí),不管是否執(zhí)行成功,都立即返回。比方調(diào)用receive()函數(shù)讀取網(wǎng)絡(luò)緩沖區(qū)中數(shù)據(jù),不管是否讀到數(shù)據(jù)都立即返回,而不會(huì)一直掛在此函數(shù)調(diào)用上。在實(shí)際Windows網(wǎng)絡(luò)通信軟件開發(fā)中,異步非阻塞套接字是用的最多的。平常所說的C/S結(jié)構(gòu)的軟件就是異步非阻塞模式的。本軟件也采用異步非阻塞模式,發(fā)送和接收消息是通過send()和receive()函數(shù)實(shí)現(xiàn)的,首先從編輯框里得到要發(fā)送的數(shù)據(jù)及其長(zhǎng)度,然后調(diào)用send()發(fā)送給對(duì)方,同時(shí)可以接收來自對(duì)方的消息,具體操作如下: ①發(fā)送客戶端:定義局部變量iLength表示發(fā)送數(shù)據(jù)長(zhǎng)度,iSentmessage表連接狀態(tài),用字符串m_strMessage;編輯要發(fā)送的信息,用戶將要發(fā)送的信息輸入編輯框EDIT1,傳遞給變量m_strMess,在不是空字符串的情況下操作,首先將值賦予m_strMessage,用GetLength()計(jì)算其長(zhǎng)度,然后調(diào)用Send函數(shù),通過m_ConnectSocket.對(duì)象發(fā)送給對(duì)方;在連接沒錯(cuò)誤的情況下,取得系統(tǒng)時(shí)間,GetLocalTime(&tm),格式設(shè)置為“年/月/日時(shí)/分/秒〞Format("%y/%m/%d%H:%M:%S"),然后在自己對(duì)話框上顯示已經(jīng)發(fā)送的消息;最后將記錄保存,fp=fopen("f:\\socket.txt","ab+")。效勞器端:定義局部變量iLength表示發(fā)送數(shù)據(jù)長(zhǎng)度,iSentmessage表連接狀態(tài),用字符串m_strMessage;編輯要發(fā)送的信息,用戶將要發(fā)送的信息輸入編輯框EDIT1,傳遞給變量m_strMsg,在不是空字符串的情況下操作,首先將值賦予m_strMessage,用GetLength()計(jì)算其長(zhǎng)度,然后調(diào)用Send函數(shù),通過m_ConnectSocket.對(duì)象發(fā)送給對(duì)方;在連接沒錯(cuò)誤的情況下,取得系統(tǒng)時(shí)間,GetLocalTime(&tm),格式設(shè)置為“年/月/日時(shí)/分/秒〞Format("%y/%m/%d%H:%M:%S"),然后在自己對(duì)話框上顯示已經(jīng)發(fā)送的消息;最后將記錄保存,fp=fopen("f:\\socket.txt","ab+")。 ②接收〔這是本程序的一個(gè)關(guān)鍵局部,一些文件的傳輸狀態(tài)要靠這局部決定,但不是理想解決方案,主要是在傳輸文件時(shí)用到〕。 客戶端:主要是調(diào)用函數(shù).Receive接受對(duì)方的消息,然后根據(jù)對(duì)方發(fā)送的消息判斷是否進(jìn)行文件的傳輸?shù)裙δ?;例如:?dāng)接收到消息“效勞器停止工作〞時(shí),m_bSendDataEnd設(shè)置為TRUE。 此時(shí)表示效勞器不再接收文件,然后客戶端再根據(jù)這個(gè)消息作出下一步的動(dòng)作,具體操作在講到。 6、終止連接客戶端:在斷開連接前,向效勞器發(fā)送消息,能夠通知效勞器自己已停止工作,然后各按鈕false。效勞器:在斷開連接前,向客戶端發(fā)送消息,能夠通知客戶端自己已停止工作,然后各按鈕false。實(shí)現(xiàn)傳輸文件的功能 由于考慮到網(wǎng)絡(luò)問題,限制為發(fā)送文件時(shí)不能同時(shí)接收文件,接收時(shí)也不能發(fā)送文件。由按鈕BUTTON6響應(yīng)函數(shù)實(shí)現(xiàn)。 初始時(shí)要?jiǎng)?chuàng)立文件對(duì)話框dlg,如果用戶在選擇完要傳送的檔后按下ok〔或確定〕鍵的話,進(jìn)行相關(guān)操作,否那么退出;按下ok后,向?qū)Ψ桨l(fā)送通知消息"效勞器要發(fā)送文件receiveorstop",讓對(duì)方確定是接收還是拒絕,m_bSendStart一直是FALSE,因此執(zhí)行while循環(huán),不能開始創(chuàng)立發(fā)送文件線程;另外文件傳送的過程可以隨時(shí)結(jié)束,結(jié)束方式有4種情況:〔1〕在沒傳送之前:如果用戶收到對(duì)方拒絕接受的消息“客戶端拒絕傳送〞,那么設(shè)置標(biāo)志m_bSendStop位TRUE,發(fā)送方自動(dòng)退出,不再傳送文件;〔2〕在沒傳送之前:如果用戶突然不想發(fā)送文件了,這是點(diǎn)擊Stop按鈕,消息響應(yīng)函數(shù)使得m_bSendStop標(biāo)志為true,這是中斷while循環(huán),自動(dòng)退出,同時(shí)向?qū)Ψ桨l(fā)送消息〞效勞器停止傳輸〞;〔3〕在傳送過程中:如果用戶想中止,通過點(diǎn)擊Stop按鈕,這時(shí)由于是在傳送過程中,故終止的函數(shù)設(shè)置m_bSendEnd為true;(在傳送線程函數(shù)里沒傳送1k的文件就會(huì)循環(huán)詢問一次m_bSendEnd是否為true),故在確定m_bSendEnd為true后,向?qū)Ψ桨l(fā)送消息"發(fā)送端終止",然后結(jié)束退出;〔4〕在傳送過程中:如果對(duì)方中止,那么會(huì)受到消息“客戶端接收終止〞,那么設(shè)置m_bRecEnd為TRUE,同樣的在傳送線程函數(shù)里沒傳送1k的文件就會(huì)循環(huán)詢問一次m_bSendEnd是否為true,故在確定m_bSendEnd為true后,結(jié)束退出; 在沒有任何終止消息的情況下,調(diào)用函數(shù)AfxBeginThread創(chuàng)立線程,開始發(fā)送文件:首先調(diào)用Open函數(shù)翻開要傳送的文件,然后創(chuàng)立CSocket類的對(duì)象sockSrvr,開始另一個(gè)套接字,等待對(duì)方的連接;連接成功后,創(chuàng)立SSFI對(duì)象,來接收文件的信息,SSFI結(jié)構(gòu)如下:typedefstructSSFI{//SOCKET_STREAM_FILE_INFO獲取文件信息TCHARszFileTitle[128];//文件的標(biāo)題名DWORDdwFileAttributes;//文件的屬性FILETIMEftCreationTime;//文件的創(chuàng)立時(shí)間FILETIMEftLastAccessTime; //文件的最后訪問時(shí)間FILETIMEftLastWriteTime;//文件的最后修改時(shí)間DWORDnFileSizeHigh;//文件大小的高位雙字DWORDnFileSizeLow;//文件大小的低位雙字DWORDdwReserved0;//保存,為0DWORDdwReserved1;//保存,為0}SSFI,*PSSFI;//對(duì)象和指針 定義變量dwRead,來累計(jì)傳送字節(jié)數(shù),初始為0,只要比要傳送的文件小就進(jìn)行循環(huán)傳送;在循環(huán)過程中還要判斷2種中斷的方式是否發(fā)生,每次傳送過程中都要分配1024字節(jié)的空間,來存儲(chǔ)讀入的文件流,sockRecv對(duì)象調(diào)用函數(shù)Send發(fā)送這些字節(jié),每次還可以設(shè)置進(jìn)度條,以觀察傳送的狀況,百分比用GetDlgItem(IDC_STATIC1)->SetWindowText(str),進(jìn)度條用m_CtrlProgressSend.SetPos(a),當(dāng)然每次都是計(jì)算之后得到的數(shù)值;dwRead隨著傳送而增加,直到大于等于StreamFileInfo.nFileSizeLow時(shí)循環(huán)結(jié)束,進(jìn)度條和百分比分?jǐn)?shù)自動(dòng)清零,結(jié)束進(jìn)程,返回到原來狀態(tài)〔傳輸過程的界面如圖3.13〕。圖3.SEQ圖3.\*ARABIC13傳輸文件過程截圖截取屏幕類CScreen的初始化:首先由矩形類CMyTracker的對(duì)象m_rectTracker設(shè)置矩形顏色RGB(0,0,255)藍(lán)色,再由LoadCursor函數(shù)加載光標(biāo),GetSystemMetrics取得屏幕的像素,最后由CopyScreen-ToBitmap截取屏幕到位圖,由CreateRectRgn函數(shù)初始化刷新窗口區(qū)域m_rgn,以顯示動(dòng)態(tài)信息,由OnCtlColor函數(shù)設(shè)置m_rgn內(nèi)文本顏色; 鼠標(biāo)在該截圖上的操作具體由OnMouseMove實(shí)現(xiàn),在這個(gè)函數(shù)里,SendMessage發(fā)送消息WM_MOUSEMOVE,觸發(fā)CDialog類的OnMouseMove事件,然后再進(jìn)一步得到鼠標(biāo)的操作過程,如鼠標(biāo)左鍵按下,鼠標(biāo)左鍵抬起,左鍵雙擊,單擊鼠標(biāo)右鍵,不同動(dòng)作有不同的處理方法:OnLButtonDown鼠標(biāo)左鍵按下時(shí),如果是第一次,那么m_bFirstDraw位false,此時(shí)畫出最小的矩形,SetRect(point.x,point.y,point.x+4,point.y+4),然后再有此按用戶需要畫出矩形,最后PaintWindow;如果不是第一次按下,那么可以調(diào)整矩形的大小,以滿足用戶的需要,Track函數(shù)會(huì)自動(dòng)調(diào)整矩形大小,在些期間,消息歸CRectTracker內(nèi)部處理;最后觸發(fā)CDialog類的OnLButtonDown函數(shù),得到鼠標(biāo)的響應(yīng);OnLButtonUp鼠標(biāo)左鍵抬起時(shí),PaintWindow〔〕畫出已確定的矩形,最后觸發(fā)CDialog類的OnLButtonUp函數(shù),得到鼠標(biāo)的響應(yīng);OnLButtonDblClk如果在是矩形內(nèi)部雙擊,CopyScreenToBitmap〔〕函數(shù)將畫出的矩形拷貝到剪貼板上,最后觸發(fā)CDialog類的OnLButtonDblClk函數(shù),得到鼠標(biāo)的響應(yīng);OnRButtonUp鼠標(biāo)右鍵操作,如果是第一次按下,那么m_bFirstDraw位true,進(jìn)行下面操作,如果已經(jīng)截取矩那么去除截取矩形SetRect(-1,-1,-1,-1),否那么調(diào)用CDialog類的OnCancel()退出;⑵在m_rgn內(nèi)顯示動(dòng)態(tài)信息——GetRValue可以得到屏幕像素的值,定義CString類的函數(shù)string,用來編輯可以顯示的內(nèi)容,最后由SetWindowText顯示在該區(qū)域內(nèi);缺乏的地方是,目前還不能把截取的圖像直接顯示在編輯框。語音通信圖3.SEQ圖3.\*ARABIC14語音通信主界面當(dāng)前計(jì)算機(jī)系統(tǒng)處理聲音文件有兩種方法:一是使用現(xiàn)成的軟件,如微軟的錄音機(jī)、SoundForge、CoolEdit等軟件可以實(shí)現(xiàn)對(duì)聲音信號(hào)進(jìn)行錄音、編輯、播放的處理,但它們的功能是有限的,為了更靈活,更大限度地處理聲音數(shù)據(jù),就不得不使用另外一種方法,既利用微軟提供的多媒體效勞,在Windows環(huán)境下自己編寫程序來進(jìn)行聲音處理來實(shí)現(xiàn)一些特定的功能。Windows支持兩種RIFF(ResourceInterchangeFileFormat,資源交互文件格式)格式的音頻文件:MIDI的RMID文件和波形音頻文件格式WAVE文件,其中在計(jì)算機(jī)領(lǐng)域最常用的數(shù)字化聲音文件格式是后者,它是微軟專門為Windows系統(tǒng)定義的波形文件格式〔WaveformAudio〕,由于其擴(kuò)展名為.wav,因而該類文件也被稱為WAVE文件。為了突出重點(diǎn),有的放矢,本文涉及到的聲音文件所指的就是WAVE文件。常見的WAVE語音文件主要有兩種,分別對(duì)應(yīng)于單聲道〔11.025KHz采樣率、8Bit的采樣值〕和雙聲道〔44.1KHz采樣率、16Bit的采樣值〕。這里的采樣率是指聲音信號(hào)在進(jìn)行模→數(shù)轉(zhuǎn)換過程中單位時(shí)間內(nèi)采樣的次數(shù)。采樣值是指每一次采樣周期內(nèi)聲音模擬信號(hào)的積分值。對(duì)于單聲道聲音文件,采樣數(shù)據(jù)為八位的短整數(shù)〔shortint00H-FFH〕;而對(duì)于雙聲道立體聲聲音文件,每次采樣數(shù)據(jù)為一個(gè)16位的整數(shù)〔int〕,高八位和低八位分別代表左右兩個(gè)聲道。 要實(shí)現(xiàn)點(diǎn)對(duì)點(diǎn)語音通信,只要針對(duì)一個(gè)點(diǎn)實(shí)現(xiàn)話音的實(shí)時(shí)采集、處理、播放,同時(shí)能進(jìn)行可靠的傳送和接收,這樣兩點(diǎn)一連便可通話。對(duì)于前者,采用WindowsMDK的低層音頻效勞比擬適宜,因?yàn)榈蛯右纛l效勞中的回調(diào)機(jī)制為我們提供了很大的方便。當(dāng)應(yīng)用程序不斷向設(shè)備驅(qū)動(dòng)程序提供音頻數(shù)據(jù)時(shí),設(shè)備驅(qū)動(dòng)過程控制音頻設(shè)備在后臺(tái)完成錄音和放音的具體操作,通過回調(diào)機(jī)制,我們又可以檢測(cè)到什么時(shí)候用完一個(gè)數(shù)據(jù)塊,并及時(shí)傳送下一個(gè)數(shù)據(jù)塊,從而保證了聲音的連續(xù),有了這種單機(jī)上的實(shí)時(shí)采集、回放功能后,接下來的工作就是在網(wǎng)絡(luò)上傳送話音數(shù)據(jù)。在點(diǎn)對(duì)點(diǎn)網(wǎng)絡(luò)傳輸方面,選擇面向連接的TCP協(xié)議,TCP傳輸協(xié)議自動(dòng)處理分組喪失和交付失序問題,這樣我們不用為這些問題操心,只需很好地利用這個(gè)連接,在采集話音回放之前一方面將自己的話音傳給網(wǎng)絡(luò),另一方面接收網(wǎng)絡(luò)傳來的話音,這樣便實(shí)現(xiàn)了點(diǎn)對(duì)點(diǎn)語音通信?!脖境绦蜻€沒有完全實(shí)現(xiàn)這個(gè)功能〕。 以下是本程序的實(shí)現(xiàn)過程: 初始時(shí),分配兩個(gè)緩沖區(qū)pBuffer1和pBuffer2,用于存儲(chǔ)聲音信息,大小為16384字節(jié)〔可自己設(shè)定〕,分配成功后,初始化WAVE波形的采集參數(shù),聲道設(shè)為1,采樣率11025,數(shù)據(jù)位設(shè)為8位等。然后用waveInOpen函數(shù)翻開錄音設(shè)備,以初始化WAVE波形的頭信息,waveInPrepareHeader為錄音設(shè)備準(zhǔn)備緩存后,waveInAddBuffer/給輸入設(shè)備增加一個(gè)緩存,開始錄音,調(diào)用waveInStart函數(shù),開始Audio_Listen_CThread和Audio_Send_CThread進(jìn)程; ①Audio_Listen_CThread:聲音文件接受線程 先定義CSocket類的對(duì)象m_Server,調(diào)用Create,Listen,等待對(duì)方連接,連接成功后,開始循環(huán)接收聲音文件,首先接收文件長(zhǎng)度,接下來開辟length長(zhǎng)的內(nèi)存空間,內(nèi)存申請(qǐng)成功,可以進(jìn)行循環(huán)檢測(cè)接受,每輪聲音文件接收完畢 后,都要檢查是否地址越界;接受完畢后,關(guān)閉SOCKET連接; ②Audio_Send_CThread:聲音文件發(fā)送線程 先定義CSocket類的對(duì)象m_Client,調(diào)用Connect函數(shù),建立與對(duì)方的連接,循環(huán)檢測(cè)發(fā)送聲音文件,首先發(fā)送塊的長(zhǎng)度,其次發(fā)送塊的內(nèi)容;用dwSent表示已經(jīng)發(fā)送的字節(jié)數(shù),發(fā)送聲音文件開始,每輪聲音文件發(fā)送完畢后,都要檢查是否地址越界;接受完畢后,關(guān)閉SOCKET連接;遠(yuǎn)程控制此功能類似于QQ的遠(yuǎn)程協(xié)助,但有很大的局限性,僅能夠鎖定或解鎖對(duì)方鍵盤,鼠標(biāo),得到對(duì)方進(jìn)程和殺死某個(gè)進(jìn)程。對(duì)于每個(gè)功能,過程相似:首先客戶端向效勞器發(fā)出請(qǐng)求,效勞器同意后建立連接,然后用戶如果想執(zhí)行某個(gè)功能,例如鎖定鼠標(biāo),那么點(diǎn)擊“鎖定鼠標(biāo)〞按鈕,客戶端向效勞器發(fā)送一個(gè)標(biāo)志字符,通知效勞器要進(jìn)行這項(xiàng)操作;效勞器收到消息后根據(jù)標(biāo)志字符判斷屬于哪項(xiàng)操作,然后作出相應(yīng)操作,對(duì)于“鎖定鼠標(biāo)〞,那么修改注冊(cè)表項(xiàng),使其無法工作,下面是操作主界面〔如圖3.15〕:圖3.SEQ圖3.\*ARABIC15遠(yuǎn)程控制主界面對(duì)于具體的功能操作詳細(xì)說明如下: 1、得到對(duì)方機(jī)器信息 客戶端要向效勞器發(fā)送消息“I〞,效勞器收到并做出判斷后,啟動(dòng)進(jìn)程++:首先通過gethostname函數(shù)得到主機(jī)名strMsg;調(diào)用庫(kù)函數(shù)GetSystemInfo得到系統(tǒng)信息:內(nèi)存大小Memory,操作系統(tǒng)類型os,屏幕分辨率display等;最后向客戶端發(fā)送標(biāo)志“J〞,表示要發(fā)送的是系統(tǒng)信息,發(fā)送完后,關(guān)閉連接。在客戶端,接收到“J〞后,做出判斷,知道收到了系統(tǒng)信息,然后根據(jù)信息里的特征,區(qū)分出各種信息,在列表框中顯示出來; 2、得到進(jìn)程信息客戶端要首先創(chuàng)立套接字sockClient,用于向效勞器發(fā)送請(qǐng)求消息,連接成功后,發(fā)送“P〞到對(duì)方,表示要得到進(jìn)程信息,然后等待對(duì)方傳送進(jìn)程信息給自己;在成員函數(shù)ReceiveFileMsg中,判斷效勞器向自己發(fā)送的是那種信息,如果是“P〞,那么表示是進(jìn)程信息,此時(shí),分配500字節(jié)的緩沖區(qū)buff,用于接受消息,將值傳遞給m_message,在編輯框IDC_MESSAGE內(nèi)顯示信息;本過程用到函數(shù)OnLookprc,和_LookPrcThread。效勞器端首先要通過收到的消息來判斷進(jìn)行那種操作,如果收到“P〞,那么開始進(jìn)程LookPrc,開始監(jiān)聽進(jìn)程,用CreateToolhelp32Snapshot函數(shù)得到進(jìn)程使用的堆[HEAP]、模塊[MODULE]、線程[THREAD]〕建立一個(gè)快照snapshot,參數(shù)SNAPPROCESS表示在快照中包含系統(tǒng)中所有的進(jìn)程,定義變量shSmal獲得有關(guān)文件關(guān)聯(lián)圖標(biāo),變量ProcessInfo聲明進(jìn)程信息變量,然后用函數(shù)Process32First(SnapShot,&ProcessInfo)返回系統(tǒng)中第一個(gè)進(jìn)程的信息;假設(shè)Status為真,進(jìn)行循環(huán),進(jìn)程計(jì)數(shù)器m_nProcess累加,函數(shù)SHGetFileInfo獲取進(jìn)程文件信息,傳給字符串prc;循環(huán)結(jié)束后,創(chuàng)立客戶端套接字,連接到另一端,如果連接成功,那么發(fā)送"P"到對(duì)方,表示傳送的是進(jìn)程信息,然后傳送進(jìn)程信息pro給對(duì)方;本過程用到函數(shù)LookPrc,_LookPrcThread。對(duì)話框如圖3.16。圖3.SEQ圖3.\*ARABIC16得到對(duì)方進(jìn)程信息的界面 3、殺死對(duì)方進(jìn)程客戶端首先要定義變量PrcName表示要?dú)⑺赖倪M(jìn)程,鼠標(biāo)在進(jìn)程列表上點(diǎn)擊要?dú)⑺赖倪M(jìn)程,用GetText函數(shù)可以得到進(jìn)程名稱,然后傳遞給變量PrcName,在確定要?dú)⑺涝撨M(jìn)程后,便啟動(dòng)進(jìn)程_KissPrcThread;該進(jìn)程首先與效勞器建立連接,然后向效勞器發(fā)送消息“E〞〔表示要進(jìn)行殺死進(jìn)程操作〕和要?dú)⑺赖倪M(jìn)程名PrcName,效勞器收到并判斷出后,開始進(jìn)程_KissPrc;首先得到進(jìn)程快照snapshot,用Process32First函數(shù)返回系統(tǒng)中第一個(gè)進(jìn)程的信息,結(jié)束進(jìn)程用到TerminateProcess(hProcess,1);然后重新掃描系統(tǒng)進(jìn)程,向客戶端發(fā)送并顯示當(dāng)前的進(jìn)程; 4、鎖定和解鎖鍵盤首先定義效勞器端的鍵盤注冊(cè)表鍵值KEY_DisableTaskMgr客戶端要向效勞器發(fā)送消息“K〞,效勞器初始設(shè)置LockOrUnLockKey為true,收到“K〞并判斷出后,設(shè)置KeyMouse為TRUE,開始進(jìn)程LockKeyBord;在函數(shù)里調(diào)用PostMessage(pDlg->GetSafeHwnd(),STATUS_MESSAGE,0,0);用GetSafeHwnd翻開平安窗口,將消息傳遞給STATUS_MESSAGE,然后調(diào)用Onkey函數(shù)進(jìn)行具體操作;(1)如果KKeyBord和LockOrUnLockKey為TRUE,用RegOpenKey函數(shù)翻開注冊(cè)表鍵KEY_DisableTaskMgr,然后RegSetValueEx修改VAL_DisableTaskMgr健值為1〔鎖定鍵盤〕,LockOrUnLockKey取反;(2)如果KKeyBord為true且LockOrUnLockKey為false,那么修改VAL_DisableTaskMgr健值為0。過程中會(huì)彈出要修改注冊(cè)表選項(xiàng)的對(duì)話框〔如圖3.17〕:圖3.SEQ圖3.\*ARABIC17程序修改注冊(cè)表的界面--鎖定/解鎖鍵盤 5、鎖定和解鎖鼠標(biāo)首先定義效勞器端的鍵盤注冊(cè)表鍵值Mouse_DisableTaskMgr??蛻舳艘蛐谄靼l(fā)送消息“S〞,效勞器初始設(shè)置LockOrUnLockMouse為true,收到“S〞并判斷出后,設(shè)置KeyMouse為TRUE,開始進(jìn)程LockMouse;在函數(shù)里調(diào)用PostMessage(pDlg->GetSafeHwnd(),STATUS_MESSAGE1,0,0);用GetSafeHwnd翻開平安窗口,將消息傳遞給STATUS_MESSAGE1,然后調(diào)用OnMouse函數(shù)進(jìn)行具體操作;(1)如果KeyMouse和LockOr-UnLockMouse為TRUE,用RegOpenKey函數(shù)翻開注冊(cè)表鍵Mouse_Disable-TaskMgr,然后RegSetValueEx修改VAL_DisableTaskMgr健值為1〔鎖定鼠標(biāo)〕,LockOrUnLockMouse取反;(2)如果KeyMouse為true且LockOr-UnLockMouse為false,那么修改VAL_DisableTaskMgr健值為0。過

溫馨提示

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

評(píng)論

0/150

提交評(píng)論