VB6里用CMD管道或SHELL命令去执行外部的EXE程序,这个EXE程序调用一个资源包,当我在VB6程序里执行这个EXE的时候,整个VB6窗体 就出现卡死状态,等外部EXE初始化这个资源包以后,程序才回答正常响应状态,提示执行完毕!其他中间过程根本无法和用户交互!当然如果这个资源包比较 小,比如只有1M以内,那么很快程序就能反映过来,大到几M以后,就总有一个卡死状态,试过了加doevents转让控制权,可是程序依然会卡死!不知道 这种情况下,如何防止其假死,其他比如VC或。NET都可以用多进程,但是VB6里好象即使用了多进程也不稳定,不知道该如何解决这种情况,非常感谢!
1、你是不是加了什么同步Shell的代码?
2、你调用的外部程序本身,可能就很霸道,这种程序,不用VB调用,就是正常双击执行,也会让整个系统半天没响应?
那1的可能性比较大,但是我不知道你所说的同步shell是何意思,那代码该如何修改呢?
我用的执行命令代码如下:
Public Function ExecuteCommand(CommandLine As String) As String
'管道方式执行DOS命令并返回执行结果
Const BuffSize As Long = 1024
Dim proc As PROCESS_INFORMATION
Dim Ret As Long
Dim start As STARTUPINFO
Dim sa As SECURITY_ATTRIBUTES
Dim hReadPipe As Long, hWritePipe As Long, lngBytesread As Long
Dim strBuff As String * BuffSize, mOutputs As String
sa.nLength = Len(sa)
sa.bInheritHandle = 1&
sa.lpSecurityDescriptor = 0&
Ret = CreatePipe(hReadPipe, hWritePipe, sa, 0)
If Ret = 0 Then ExecuteCommand = "CreatePipe Failed. Error: " & Err.LastDllError & vbCrLf: Exit Function
start.cb = Len(start)
start.dwFlags = &H100 Or 1
start.hStdOutput = hWritePipe
start.hStdError = hWritePipe
Ret& = CreateProcessA(0&, CommandLine, sa, sa, 1, &H20, 0, 0, start, proc)
If Ret <> 1 Then ExecuteCommand = "错误: '" & CommandLine & "' 不是可运行的程序" & vbCrLf: Exit Function
Ret = CloseHandle(hWritePipe) mOutputs = ""
Do
Ret = ReadFile(hReadPipe, strBuff, BuffSize, lngBytesread, 0&)
If Ret = 0 Then Exit Do
mOutputs = mOutputs & LeftB(StrConv(strBuff, vbFromUnicode), lngBytesread)
Loop
Ret = CloseHandle(proc.hProcess)
Ret = CloseHandle(proc.hThread)
Ret = CloseHandle(hReadPipe)
ExecuteCommand = Replace(StrConv(mOutputs, vbUnicode), Chr(0), "")
End Function
管道本身就是同步机制,子进程写管道,必须等写完内容才能返回,父进程读也是这样,必须等子进程关闭全部写Handle,才会返回0
子进程不主动关闭写Handle,父进程将一直挂着,就是假死。
这种情况DoEvents,肯定没用,因为它是在Api调用中挂起的,根本不会执行其它语句。
要解决问题,估计只有修改那个外部exe。