我是靠谱客的博主 超帅戒指,最近开发中收集的这篇文章主要介绍VC中调用CMD命令并获取调用结果,觉得挺不错的,现在分享给大家,希望可以做个参考。

概述

    主要实现方法是建立一个新进程,用于运行一个隐藏窗口的CMD程序,进而通过匿名管道获取执行结果。注意一点,这样的方法每执行一条命令都会打开一个新的CMD窗口,只不过普通命令在执行完后会自动关闭。但是,ping命令加上参数“-t”,将会一直执行,所以相对应的CMD窗口也会一直存在,需要自行关闭。

    另外,外了防止程序假死,创建一个新线程用于获取执行CMD命令的结果。

下面是具体实现:


1、创建基于对对话框的应用程序,放置两个Edit控件,使用默认ID,再添加一个按钮。

声明一个线程函数:

// 声明线程函数
	static DWORD WINAPI ThreadFun(LPVOID lpParam);

2、声明几个全局变量

// 全局变量
HANDLE h1 = NULL;                // 线程句柄
DWORD pid = 0;                   // 保存cmd窗口的PID
CString inputCmd, outputCmd;     // 保存cmd命令和返回的结果
CEdit * m_edit;                  // 输出框

3、线程函数的实现:

/************************************************************************/
/* 线程函数                                                             */
/************************************************************************/
DWORD WINAPI CSysCmdTestDlg::ThreadFun(LPVOID lpParam)
{
	SECURITY_ATTRIBUTES sa;
    HANDLE hRead,hWrite;
	
    sa.nLength = sizeof(SECURITY_ATTRIBUTES);    
    sa.lpSecurityDescriptor = NULL;        //使用系统默认的安全描述符    
    sa.bInheritHandle = TRUE;              //创建的进程继承句柄
	
    if (!CreatePipe(&hRead,&hWrite,&sa,0)) //创建匿名管道
    {        
        ::MessageBox(NULL,"CreatePipe Failed!","提示",MB_OK | MB_ICONWARNING);        
        return 0;
    }
    
    STARTUPINFO si;    
    PROCESS_INFORMATION pi;
	
    ZeroMemory(&si,sizeof(STARTUPINFO));
    si.cb = sizeof(STARTUPINFO);    
    GetStartupInfo(&si);    
    si.hStdError = hWrite;    
    si.hStdOutput = hWrite;    //新创建进程的标准输出连在写管道一端
    si.wShowWindow = SW_HIDE;  //隐藏窗口    
    si.dwFlags = STARTF_USESHOWWINDOW | STARTF_USESTDHANDLES;
	
    
    char cmdline[200]; 
    CString tmp,stredit2;
	
    tmp.Format("cmd /C %s",inputCmd);  // inputCmd为输入的cmd命令
    sprintf(cmdline,"%s",tmp);
	
    if (!CreateProcess(NULL,cmdline,NULL,NULL,TRUE,NULL,NULL,NULL,&si,&pi)) //创建子进程
    {
        ::MessageBox(NULL,"CreateProcess Failed!","提示",MB_OK | MB_ICONWARNING);        
        return 0;
    }

	pid = pi.dwProcessId;

    CloseHandle(hWrite); //关闭管道句柄
    
    char buffer[4096] = {0};
    DWORD bytesRead;
	
    while (true) 
    {
        if (ReadFile(hRead,buffer,4095,&bytesRead,NULL) == NULL) //读取管道
            break;

		CString temp;
        temp = buffer; // outpuuCmd为输出的结果

		temp += _T("rnrn");

		outputCmd += temp;
		
		//显示输出信息到编辑框,并刷新窗口
		int len = outputCmd.GetLength();
		m_edit->SetWindowText(outputCmd);
		m_edit->SetSel(len, len);
		
    }
    CloseHandle(hRead);

	return 1;
}

4、添加一个按钮,响应函数为:

void CSysCmdTestDlg::OnButton1() 
{
	// TODO: Add your control notification handler code here

	GetDlgItemText(IDC_EDIT2,inputCmd); //获取编辑框中输入的命令行

	// 关闭CMD窗口
	::SendMessage(GetWindowHandleByPID(pid), WM_CLOSE, NULL, NULL);

	// 销毁线程
	CloseHandle(h1);

	// 创建线程
	h1 = ::CreateThread(NULL, 0, ThreadFun, NULL, 0, 0);
}

5、程序退出时的一些处理:

响应WM_CLOSE消息

void CSysCmdTestDlg::OnClose() 
{
	// TODO: Add your message handler code here and/or call default
	
	// 关闭CMD窗口
	::SendMessage(GetWindowHandleByPID(pid), WM_CLOSE, NULL, NULL);

	// 销毁线程
	CloseHandle(h1);

	CDialog::OnClose();
}

6、下面是程序截图:










最后,程序源代码:http://download.csdn.net/detail/wwkaven/7555011

最后

以上就是超帅戒指为你收集整理的VC中调用CMD命令并获取调用结果的全部内容,希望文章能够帮你解决VC中调用CMD命令并获取调用结果所遇到的程序开发问题。

如果觉得靠谱客网站的内容还不错,欢迎将靠谱客网站推荐给程序员好友。

本图文内容来源于网友提供,作为学习参考使用,或来自网络收集整理,版权属于原作者所有。
点赞(67)

评论列表共有 0 条评论

立即
投稿
返回
顶部