VC下面执行DOS命令

本文参考如下文档:

vc下执行DOS命令

vc下执行DOS命令

后者也是转载前者,但代码排版看起来好一些。

在上面的基础上,又对代码做了一点改动,主要是加了日志文件,方便看到DOS命令中间执行结果。

下面的示例代码是以VC6为例,一个workspace中包括两个project,一个是简单的MFC对话框,另外一个是执行dos命令的lib。lib的宏定义参考了pcre的风格,参考Windows上面编译pcre的步骤

lib包括两个文件:DosCommand.h,.c。代码如下:

DosCommand.h:

#ifndef __DOS_COMMAND_H
#define __DOS_COMMAND_H


#ifndef DOS_COMMAND_EXP_DECL
#  ifdef _WIN32
#    ifndef DOS_COMMAND_STATIC
#      define DOS_COMMAND_EXP_DECL extern __declspec(dllimport)
#    endif
#  endif
#endif

/* By default, we use the standard "extern" declarations. */

#ifndef DOS_COMMAND_EXP_DECL
#  ifdef __cplusplus
#    define DOS_COMMAND_EXP_DECL       extern "C"
#  else
#    define DOS_COMMAND_EXP_DECL       extern
#  endif
#endif

/* Have to include stdlib.h in order to ensure that size_t is defined;
it is needed here for malloc. */

#include <stdlib.h>

/* Allow for C++ users */

#ifdef __cplusplus
extern "C" {
#endif



#include <windows.h>

/*

The output of the dos command will be writen to a file specified by <fileName>.

e.g.: 
command: ipconfig /all
fileName: c:\\test.txt
*/
DOS_COMMAND_EXP_DECL BOOL ExecuteDosCommand(const char* command, const char* fileName);


#ifdef __cplusplus
}  /* extern "C" */
#endif

#endif

DosCommand.cpp的代码:

#include "DosCommand.h"

#ifndef DOS_COMMAND_EXP_DECL
#  ifdef _WIN32
#    ifdef DLL_EXPORT
#      define DOS_COMMAND_EXP_DECL       extern __declspec(dllexport)
#      define DOS_COMMAND_EXP_DEFN       __declspec(dllexport)
#      define DOS_COMMAND_EXP_DATA_DEFN  __declspec(dllexport)
#    else
#      define DOS_COMMAND_EXP_DECL       extern
#      define DOS_COMMAND_EXP_DEFN
#      define DOS_COMMAND_EXP_DATA_DEFN
#    endif
#
#  else
#    ifdef __cplusplus
#      define DOS_COMMAND_EXP_DECL       extern "C"
#    else
#      define DOS_COMMAND_EXP_DECL       extern
#    endif
#    ifndef DOS_COMMAND_EXP_DEFN
#      define DOS_COMMAND_EXP_DECL       DOS_COMMAND_EXP_DECL
#    endif
#    ifndef DOS_COMMAND_EXP_DATA_DEFN
#      define DOS_COMMAND_EXP_DATA_DEFN
#    endif
#  endif
#endif

#include <stdio.h>
#include <windows.h>

enum {BUFFER_SIZE = 4096};

static HANDLE hOutput = NULL;

static void MyCreateFile(const char* fileName);
static void MyWriteFile(const char* info);
static void MyCloseFile();

DOS_COMMAND_EXP_DECL BOOL ExecuteDosCommand(const char* command, const char* fileName)
{
    SECURITY_ATTRIBUTES security_attributes = {0};
    HANDLE hReadPipe = NULL;
    HANDLE hWritePipe = NULL;

    char dos_command[512];
    STARTUPINFO startUpInfo;
    PROCESS_INFORMATION processInfo;

    char buffer[BUFFER_SIZE] = {0};
    DWORD dwRead;

    if (NULL == command || strlen(command) > 1024) return FALSE;

    printf("%s", command);

    security_attributes.nLength = sizeof(SECURITY_ATTRIBUTES);
    security_attributes.lpSecurityDescriptor = NULL;
    security_attributes.bInheritHandle = TRUE;

    if (!CreatePipe(&hReadPipe, &hWritePipe, &security_attributes, 0)) {
        return FALSE;
    }

    strcpy(dos_command, "Cmd.exe /C ");
    strcat(dos_command, command);

    startUpInfo.cb = sizeof(STARTUPINFO);
    GetStartupInfo(&startUpInfo);

    startUpInfo.hStdError = hWritePipe;
    startUpInfo.hStdOutput = hWritePipe;
    startUpInfo.wShowWindow = SW_HIDE;
    startUpInfo.dwFlags = STARTF_USESHOWWINDOW | STARTF_USESTDHANDLES;  

    if (!CreateProcess(NULL, dos_command, NULL, NULL, TRUE, 0, NULL, NULL, &startUpInfo, &processInfo)) {
        CloseHandle(hWritePipe);
        CloseHandle(hReadPipe);
        return FALSE;
    }
    Sleep(1000); // Need to be refactored.
    CloseHandle(hWritePipe);

    MyCreateFile(fileName);
    for (;;) {
        if (!ReadFile(hReadPipe, buffer, 4095, &dwRead, NULL)) break;

        MyWriteFile(buffer);
    }

    MyCloseFile();

    CloseHandle(hReadPipe);
    return TRUE; 
}

void MyCreateFile(const char* fileName)
{
    if (hOutput != NULL) MyCloseFile();

    hOutput = CreateFile(fileName, 
        GENERIC_WRITE,
        FILE_SHARE_READ,
        NULL,
        CREATE_ALWAYS,
        FILE_ATTRIBUTE_NORMAL,
        NULL);

    if (INVALID_HANDLE_VALUE == hOutput) hOutput = NULL;

}

void MyWriteFile(const char* info)
{
    DWORD dwWritten = 0;

    if (NULL == hOutput) return;

    WriteFile(hOutput, info, strlen(info), &dwWritten, NULL);
}

void MyCloseFile()
{
    if (NULL == hOutput) return;

    CloseHandle(hOutput);
    hOutput = NULL;
}

对话框exe对应的project,在生成的代码基础上,增加如下部分:

#include "CommandLib/DosCommand.h"

#ifdef _DEBUG
#pragma comment(lib, "CommandLib/Debug/CommandLib.lib")
#else
#pragma comment(lib, "CommandLib/Release/CommandLib.lib")
#endif

void CExeDosCmdDlg::OnOK() 
{
    ExecuteDosCommand("dir", "c:\\test.txt");

    CDialog::OnOK();
}

另外,两个project中需要设置的宏:

  • lib: DLL_EXPORT,DOS_COMMAND_STATIC
  • exe: DOS_COMMAND_STATIC

源代码工程参考附件:
VC中执行DOS命令,获取返回值的例子

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值