function RunDOS(const CommandLine: string): string;
var
  HRead, HWrite: THandle;
  StartInfo: TStartupInfo;
  ProceInfo: TProcessInformation;
  b: Boolean;
  sa: TSecurityAttributes;
  inS: THandleStream;
  sRet: TStrings;
begin
  Result := '';
  FillChar(sa, sizeof(sa), 0);
//设置允许继承,否则在NT和2000下无法取得输出结果
  sa.nLength := sizeof(sa);
  sa.bInheritHandle := True;
  sa.lpSecurityDescriptor := nil;
  b := CreatePipe(HRead, HWrite, @sa, 0);
  Assert(b);

FillChar(StartInfo, SizeOf(StartInfo), 0);
  StartInfo.cb := SizeOf(StartInfo);
  StartInfo.wShowWindow := SW_HIDE;
//使用指定的句柄作为标准输入输出的文件句柄,使用指定的显示方式
  StartInfo.dwFlags := STARTF_USESTDHANDLES or STARTF_USESHOWWINDOW;
  StartInfo.hStdError := HWrite;
  StartInfo.hStdInput := GetStdHandle(STD_INPUT_HANDLE); //HRead;
  StartInfo.hStdOutput := HWrite;
 
  b := CreateProcess(nil, //lpApplicationName: PChar
    PChar(CommandLine), //lpCommandLine: PChar
    nil, //lpProcessAttributes: PSecurityAttributes
    nil, //lpThreadAttributes: PSecurityAttributes
    True, //bInheritHandles: BOOL
    CREATE_NEW_CONSOLE,
    nil,
    nil,
    StartInfo,
    ProceInfo);
 
  Assert(b);
  WaitForSingleObject(ProceInfo.hProcess, INFINITE);

inS := THandleStream.Create(HRead);
  if inS.Size > 0 then
  begin
    sRet := TStringList.Create;
    sRet.LoadFromStream(inS);
    Result := sRet.Text;
    sRet.Free;
  end;
  inS.Free;

CloseHandle(HRead);
  CloseHandle(HWrite);
end;

这个函数在长时间运行dos命令时,会发生无法退出的问题,因此需要另一个实现版本:

function GetDosOutput(Command: string): string;
var
hReadPipe : THandle;
hWritePipe : THandle;
SI : TStartUpInfo;
PI : TProcessInformation;
SA : TSecurityAttributes;
BytesRead : DWORD;
Dest : array[0..32767] of char;
CmdLine : array[0..512] of char;
Avail, ExitCode, wrResult : DWORD;
osVer : TOSVERSIONINFO;
tmpstr :AnsiString;
Line: String;
begin
osVer.dwOSVersionInfoSize := Sizeof(TOSVERSIONINFO);
GetVersionEX(osVer);
if osVer.dwPlatformId = VER_PLATFORM_WIN32_NT then
begin
    SA.nLength := SizeOf(SA);
    SA.lpSecurityDescriptor := nil;
    SA.bInheritHandle := True;
    CreatePipe(hReadPipe, hWritePipe, @SA, 0);
end
else
    CreatePipe(hReadPipe, hWritePipe, nil, 1024);
try
    FillChar(SI, SizeOf(SI), 0);
    SI.cb := SizeOf(TStartUpInfo);
    SI.wShowWindow := SW_HIDE;
    SI.dwFlags := STARTF_USESHOWWINDOW;
    SI.dwFlags := SI.dwFlags or STARTF_USESTDHANDLES;
    SI.hStdOutput := hWritePipe;
    SI.hStdError := hWritePipe;
    StrPCopy(CmdLine, Command);
    if CreateProcess(nil, CmdLine, nil, nil, True, NORMAL_PRIORITY_CLASS, nil, nil, SI, PI) then
    begin
       ExitCode := 0;
       while ExitCode = 0 do
       begin
          wrResult := WaitForSingleObject(PI.hProcess, 1000);
          if PeekNamedPipe(hReadPipe, @Dest[0], 32768, @Avail, nil, nil) then
          begin
             if Avail > 0 then
             begin
               try
                 FillChar(Dest, SizeOf(Dest), 0);
                 ReadFile(hReadPipe, Dest[0], Avail, BytesRead, nil);
                 TmpStr := Copy(Dest,0 , BytesRead-1);
                 Line:=Line+TmpStr; 
               Except
               end;
             end;
          end;
            if wrResult <> WAIT_TIMEOUT then ExitCode := 1;
       end;
       GetExitCodeProcess(PI.hProcess, ExitCode);
       CloseHandle(PI.hProcess);
       CloseHandle(PI.hThread);
     end;
     finally
       if line='' then line:='NULL';    //命令没有输出回应!
       result:=Line;
       CloseHandle(hReadPipe);
       CloseHandle(hWritePipe);
   end;
end;

http://blog.csdn.net/henreash/article/details/7095744

运行Dos命令并得到dos的输出文本(使用管道函数CreatePipe和PeekNamedPipe)的更多相关文章

  1. dos命令记录以及dos下通过进程id查找工作路径

    dos命令 tasklist |findstr "1696" 通过进程id查看进程名 tasklist 列出所有进程 netstat -ano 查看当前网络通信进程连接的各种状态 ...

  2. Windows常用的一些DOS命令整理

    Windows常用的一些DOS命令整理.. MS DOS 命令大全 ---清空Dos屏幕使用命令:cls -- Dos切换当前目录到D盘:cd d: 一.基础命令 1 dir 无参数:查看当前所在目录 ...

  3. dos命令大全 黑客必知的DOS命令集合

    dos命令大全 黑客必知的DOS命令集合 一般来说dos命令都是在dos程序中进行的,如果电脑中安装有dos程序可以从开机选项中选择进入,在windows 系统中我们还可以从开始运行中输入cmd命令进 ...

  4. Dos命令大全完整版

    DOS(磁盘操作系统)命令,是DOS操作系统的命令,是一种面向磁盘的操作命令,主要包括目录操作类命令.磁盘操作类命令.文件操作类命令和其它命令. 使用技巧 DOS命令不区分大小写,比如C盘的Progr ...

  5. C#执行外部程序之执行DOS命令和批处理

    在项目开发中,有时候要处理一些文件,比如视频格式的转换,如果用C开发一套算法,再用C#调用,未免得不偿失!有时候调用现有的程序反而更加方便.今天就来说一下C#中如何调用外部程序,执行一些特殊任务. 这 ...

  6. C#执行DOS命令(CMD命令)

    在c#程序中,有时会用到调用cmd命令完成一些功能,于是在网上查到了如下方法,实现了c#执行DOS命令,并返回结果.         //dosCommand Dos命令语句         publ ...

  7. 在.net中悄悄执行dos命令,并获取执行的结果(转)

    一.怎样使dos命令悄悄执行,而不弹出控制台窗口? 1.需要执行带“/C”参数的“cmd.exe”命令,它表示执行完命令后立即退出控制台.2.设置startInfo.UseShellExecute = ...

  8. C# 执行DOS命令和批处理

    在项目开发中,有时候要处理一些文件,比如视频格式的转换,如果用C开发一套算法,再用C#调用,未免得不偿失!有时候调用现有的程序反而更加方便.今天就来说一下C#中如何调用外部程序,执行一些特殊任务. 这 ...

  9. C#中执行Dos命令

    //dosCommand Dos命令语句 public string Execute(string dosCommand) { ); } /// <summary> /// 执行DOS命令 ...

随机推荐

  1. 模拟QQ系统设置面板实现功能

    业务需求: 基于网盘客户端的实现,原有网盘的设置面板无论从界面显示还是从业务需求都不能满足我们的正常需求.当前的要求是,模拟QQ系统设置的面板实现当前我们网盘中的基本配置功能.在完成这篇文章时已将基本 ...

  2. ACM一些题目

    Low Power 先二分答案,可以通过调整证明同一台机器选的两个芯片必然是提供能量数值相邻的两个.所以再贪心一下就可以了. 时间复杂度\(O(n \log n)\). Factors 假设\(k\) ...

  3. VS2010 安装 Boost 库 1.54

    Boost库被称为C++准标准库, 功能很是强大, 下面记录我在VS2010中安装使用Boost库的过程. 首先上官网http://www.boost.org/下载最新的Boost库, 我的版本是1_ ...

  4. linux下shutdown无法关闭tomcat进程的解决方式

    1.问题 笔者在linux下发现使用tomcat6.0.41自带的./shutdown.sh常常无法停止进程,导致各种问题的发生,令笔者相当反感! 2.解决方式一: 查找到全部的tomcat进程 $ ...

  5. How to Create Dump File for Applications

    使用WinDBG这个工具,可以在应用程序异常终止或者无响应时获取它的尸体,以用来解剖研究. Creating Dump File      在Vista环境中抓取Dump文件很方便,在task man ...

  6. SqlServer和Oracle中一些常用的sql语句7 游标

    declare db_cursor4 scroll cursor for select * from 供应商 --声明游标 open db_cursor4 --打开游标 fetch first fro ...

  7. JAVA学习笔记 -- 数据结构

    一.数据结构的接口 在Java中全部类的鼻祖是Object类,可是全部有关数据结构处理的鼻祖就是Collection和Iterator接口,也就是集合与遍历. 1.Collection接口 Colle ...

  8. EasyUI - DataGrid 组建 - [ 删除,修改 ]

    效果: html代码: <div style="padding-top: 50px; width: 800px; margin: 0 auto;"> <!--使用 ...

  9. MSSQL - 多表查询

    SELECT u.UserNumber, u.UserName, c.CarNumber, c.CarName, c.CarEngine, s.BuyLs, s.BuyTime FROM Tb_Sal ...

  10. tmux centos 6.3

    tmux-1.6-1.el6.rf.i686.rpm CentOS 6 / RHEL 6 Download #21 tmux-1.6-1.el6.rf.i686.rpm