Подтвердить что ты не робот

Как проверить, запущена ли программа с консоли?

Я пишу приложение, которое сбрасывает некоторые диагностические данные на стандартный вывод.

Я хочу, чтобы приложение работало следующим образом:

  • Если он запускается из автономной командной строки (через cmd.exe) или имеет стандартный вывод, перенаправленный/подключенный к файлу, выйдите из него, как только оно закончится,
  • В противном случае (если он запускается из окна, а окно консоли генерируется автоматически), то дополнительно дождаться нажатия клавиши перед выходом (чтобы позволить пользователю прочитать диагностику), прежде чем окно исчезнет.

Как это сделать? Я подозреваю, что изучение родительского процесса может быть способом, но я действительно не в WinAPI, поэтому вопрос.

Я на MinGW GCC.

4b9b3361

Ответ 1

Вы можете использовать GetConsoleWindow, GetWindowThreadProcessId и GetCurrentProcessId.

1) Сначала вы должны получить текущий дескриптор окна консоли с помощью функции GetConsoleWindow.

2) Затем вы получите владельца процесса дескриптора окна консоли.

3) Наконец, вы сравниваете возвращаемый PID с PID вашего приложения.

Проверьте этот образец (VS С++)

#include "stdafx.h"
#include <iostream>
using namespace std;
#if       _WIN32_WINNT < 0x0500
  #undef  _WIN32_WINNT
  #define _WIN32_WINNT   0x0500
#endif
#include <windows.h>
#include "Wincon.h" 

int _tmain(int argc, _TCHAR* argv[])
{   
    HWND consoleWnd = GetConsoleWindow();
    DWORD dwProcessId;
    GetWindowThreadProcessId(consoleWnd, &dwProcessId);
    if (GetCurrentProcessId()==dwProcessId)
    {
        cout << "I have my own console, press enter to exit" << endl;
        cin.get();
    }
    else
    {
        cout << "This Console is not mine, good bye" << endl;   
    }


    return 0;
}

Ответ 2

Мне это нужно в С#. Здесь перевод:

[DllImport("kernel32.dll")]
static extern IntPtr GetConsoleWindow();

[DllImport("kernel32.dll")]
static extern IntPtr GetCurrentProcessId();

[DllImport("user32.dll")]
static extern int GetWindowThreadProcessId(IntPtr hWnd, ref IntPtr ProcessId);

static int Main(string[] args)
{
    IntPtr hConsole = GetConsoleWindow();
    IntPtr hProcessId = IntPtr.Zero;
    GetWindowThreadProcessId(hConsole, ref hProcessId);

    if (GetCurrentProcessId().Equals(hProcessId))
    {
        Console.WriteLine("I have my own console, press any key to exit");
        Console.ReadKey();
    }
    else
        Console.WriteLine("This console is not mine, good bye");

    return 0;
}

Ответ 3

Типичный тест:

if( isatty( STDOUT_FILENO )) {
        /* this is a terminal */
}

Ответ 4

I18N гуру Майкл Каплан из Microsoft предоставил серию методов в своем блоге, которые позволяют вам проверять кучу вещей на консоли, включая ли или не была перенаправлена ​​консоль.

Они написаны на С#, но перенос на C или С++ будет очень простым, поскольку все это делается с вызовами API Win32.