Есть ли какие-нибудь макросы, чтобы определить, компилируется ли мой код в Windows?
Я хотел бы определить, является ли ОС, на которой я работаю, Windows. Есть ли простой макрос, который я могу проверить, чтобы убедиться в этом?
11 ответов
[Правка: я предполагаю, что вы хотите использовать макросы времени компиляции, чтобы определить, в какой среде вы находитесь. Может быть, вы хотите определить, используете ли вы Wine под Linux или что-то вместо Windows, но в целом ваш компилятор нацелен на конкретную среду, и это либо Windows (DOS), либо нет, но это редко (никогда?) и то и другое.]
Некоторые компиляторы предлагают макросы для обозначения среды сборки Windows. Но они будут отличаться от компилятора к компилятору и даже на одном и том же компиляторе в Windows, если целевая среда не является исключительно Windows. Обычно это __WIN32__
, но не всегда.
#if defined (__WIN32__)
// Windows stuff
#endif
Иногда это может быть _WIN32
, __CYGWIN32__
или, возможно, только индикатор компилятора (_MSC_VER
).
Если вы знаете среду, в которую вы будете встраивать (из make-файла), то вы можете передать #define
в командной строке вроде g++ -D __WIN32__ yourfile.c
".
Существует несколько различных способов обнаружения сред компиляции, хоста и среды выполнения. Все зависит от того, что именно вы хотите знать. Существует три типа среды:
- Сборка: это среда, в которой компилируется программа.
- Хост: Это среда, в которой выполняется программа.
- Цель: в случае инструментов генерации кода (таких как компиляторы) именно здесь будет выполняться сгенерированный код.
Если вы выполняете кросс-компиляцию, среда сборки и хоста могут быть совершенно разными (это часто встречается при создании встроенных приложений, но не очень часто при сборке приложений для настольных ПК / серверов), и вы обычно не можете запустить скомпилированный двоичный файл в системе, используемой для скомпилируйте это. В противном случае среда хоста должна быть совместима со средой сборки: например, для создания приложения на XP, которое будет работать на Vista.
Макросы препроцессора C не могут быть использованы для того, чтобы сообщать вам детали хост-системы (то есть, на чем вы работаете); они могут только сказать вам, для чего был скомпилирован код. В случае с Windows, два наиболее важных макроса:
- _WIN32 означает, что Win32 API доступен. Он не говорит вам, какой компилятор вы используете, на самом деле _WIN32 определяется как при использовании GCC Cygwin, так и GCC MinGW. Поэтому не используйте _WIN32, чтобы выяснить, компилируете ли вы с Visual Studio.
_MSC_VER
сообщает, что программа компилируется с помощью Microsoft Visual C/C++. Ну, почти._MSC_VER
также определяется при использовании компилятора Intel C++, который предназначен для замены Visual C++.
Существует множество других макросов, описанных в документации по Visual Studio.
Если вы хотите узнать, какую именно версию Windows вы используете, вам придется использовать функции времени выполнения, такие как GetVersion() (как описано в других ответах).
Вы могли бы получить более конкретные ответы, если бы вы сказали нам, что именно вы хотите проверить.
% touch foo.C ; g++ -dM -E foo.C
Хорошо выполнит перечисление всех макросов (#define), автоматически определенных для вас вашим [машинно-зависимым] компилятором g++.
Там может быть что-то подобное для компиляторов Microsoft...
Эти три строки помогут вам в обнаружении, сначала мы или большинство предопределенных окон намекаем на одно определение макроса OS_WIN:
#iffined(_WIN32) || определено (WIN32) || определен (__CYGWIN__) || определено (__MINGW32__) || определен (__BORLANDC__) #define OS_WIN #endif
Затем вы можете проверить это с помощью препроцессора ifdef:
#ifdef OS_WIN // Специфичные для Windows вещи #else // Нормальный материал #endif
Компилятор MSVC++ (не windows.h
) определяет _WIN32
для всех сборок, так что это более безопасный макрос для проверки. Компилятор MinGW gcc тоже. Любая среда кросс-компиляции, нацеленная на Win32, должна установить это тоже.
Эта штука работает в Visual Studio 2012 и других компиляторах g ++ cgwin. Вырежьте и вставьте его, но это, как правило, настолько тонкий, насколько это возможно. Все, что он делает - это обнаруживает операционные системы Windows. Просто примените количественную оценку: если не выиграете тогда *inux:D наслаждайтесь
#include <string>
#include <iostream>
#include <fstream>
#include <cstdlib>
Using namespace std;
int main(){
char chCap; int i = 0;
const int MAX_BUFFER = 70;
char buffer[MAX_BUFFER];
string cmd="ver";
FILE *stream = _popen(cmd.c_str(), "r");
if (0 != stream){
while (!feof(stream)){
//One way is here
//chCap = fgetc(stream);
//cout << chCap;
//buffer[i++] = chCap;
//This one seams better
fgets(buffer, MAX_BUFFER, stream);
}
_pclose(stream);
}
cout << endl;
cout << buffer << endl;
//The op sys detection starts here
string opSys(buffer); //char array to string
if("Microsoft" == opSys.substr(0,9)){
cout << "You are in a Microsoft envornment " << endl;
}
system("pause");
return 0;
}
Если вы используете целевой код для MS Windows, вы можете вызвать GetVersion() или GetVersionEx() для получения дополнительной информации и для определения варианта Windows, на котором вы работаете.
Для получения дополнительной информации о MSDN.
http://msdn.microsoft.com/en-us/library/ms724451(VS.85).aspx
Ссылки, упомянутые до сих пор, указывают информацию во время компиляции. Вы можете установить флаги в этих сегментах кода во время компиляции.
Тем не менее, я думаю, что вы спрашиваете больше о том, "под какой версией windows я работаю?", А не "скомпилирован ли я для работы под windows?" Я надеюсь, что это правильное предположение.
Под C# это относительно просто. Вы можете ссылаться на System.Environment.OSVersion, а затем искать в разделе "Платформа".
Тем не менее, вы спрашиваете о C++. Какой компилятор вы используете? Это имеет большое значение в том, как вы проверяете версию операционной системы, так как нет единого стандарта для получения этой информации (который я нашел).
В Visual C++ используйте Google, чтобы найти информацию о GetVersion/GetVersionEx. Оба предоставят вам структуры, которые содержат информацию о текущей версии Windows, под которой работает программа.
На самом деле я бы пошел с окружающей средой. getenv() является стандартной библиотечной функцией и, вероятно, является единственным потенциально переносимым способом сделать это. Хитрость заключается в том, чтобы выяснить, какие переменные являются уникальными для всех ОС. В Windows есть ComSpec, appdata, Windir, systemroot и systemdrive, которые должны быть установлены. Вы также можете указать переменную пути для WINDOWS или WINNT, но это может быть неточно. Я не эксперт по оболочке Linux /Solaris/MacOS, так что кто-то другой может рассказать вам, какие "стандартные" переменные среды существуют в этих ОС. CygWin может также вызвать некоторые проблемы.
Макросы, подобные перечисленным выше, сообщат вам, была ли ваша программа скомпилирована на компьютере с Windows, а не на компьютере с Windows.
Если вы пишете что-то, что совершенно не зависит от платформы (то есть обрабатывает только открытие / чтение / обработку / запись) файловых потоков... вам придется выполнить какой-то тест, например открыть файл, который должен существовать, если на компьютере установлена Windows. Если ваша программа использует только стандартные stdio, math и т. Д., То это будет так.
В противном случае, если ваш код содержит системные вызовы Windows, он просто не будет работать на любой другой платформе.
Вы можете написать какой-нибудь макрос, например:
#define RUNNING_ON_WINDOWS ( ... some test )
Только не используйте его для условной компиляции, то есть:
if (RUNNING_ON_WINDOWS) {
...
} else
printf("Windows Required\n");
Возможно, это будет зависеть от используемого компилятора, но попробуйте:
#ifdef WIN32
...
#endif