getopt.h: Компиляция C-кода Linux в Windows

Я пытаюсь получить набор из девяти файлов * .c (и девяти связанных файлов * .h) для компиляции под Windows.

Код был первоначально разработан в Linux для приема аргументов командной строки с использованием стандартной библиотеки GNU-Linux / C "getopt.h". И эта библиотека не применяется для создания C-кода в Windows.

Я хочу проигнорировать то, что делает мой код прямо сейчас, и задать следующий вопрос. Для тех из вас, кто знаком с этой библиотекой C "getopt.h": можно ли будет собрать и запустить мой код в Windows, если это зависит от аргументов командной строки в стиле POSIX? Или мне придется переписать код, чтобы он работал в Windows, по-другому передавая входные файлы (и отказавшись от зависимости "getopt.h")?


person theJollySin    schedule 01.05.2012    source источник
comment
если поддержка MSVC не является жестким требованием, всегда есть MinGW: я вполне доволен пакетами кросс-компилятора MinGW, которые поставляются с Cygwin ...   -  person Christoph    schedule 02.05.2012
comment
getopt.h описывает API, предоставляемый методами из getopt.c. Вытащите его откуда-нибудь, скомпилируйте и свяжите результат со своим приложением, и все готово.   -  person alk    schedule 02.05.2012
comment
Просто гнида по поводу комментария алка, технически это можно сделать, но законность полностью зависит от совместимости лицензий из источников getopt (если есть) и проекта. Некоторые реализации getopt говорят, что это общественное достояние, так что это, скорее всего, не будет проблемой.   -  person    schedule 18.03.2017


Ответы (9)


Ты прав. getopt() - это POSIX, а не Windows, вам, как правило, придется переписывать весь код синтаксического анализа аргументов командной строки.

К счастью, есть проект Xgetopt, предназначенный для классов Windows / MFC.

http://www.codeproject.com/Articles/1940/XGetopt-A-Unix-compatible-getopt-for-MFC-and-Win32

Если вы можете заставить это работать в своем проекте, это должно сэкономить вам немного кода и избавить вас от необходимости переделывать весь синтаксический анализ.

Кроме того, он поставляется с красивым демонстрационным приложением с графическим интерфейсом, которое может вам пригодиться.

Удачи!

person Cloud    schedule 01.05.2012
comment
Я попробую прямо сейчас. Но я не могу сказать по указанной вами ссылке: API этой библиотеки такой же, как и старый API getopt? - person theJollySin; 02.05.2012
comment
Не могли бы вы назвать какую-нибудь причину для переписывания, кроме упражнений на синтаксический анализ? - person alk; 02.05.2012
comment
Ну, код, который я портирую (для использования в гораздо более крупной системе), имеет возраст несколько месяцев. Но люди, которые его разрабатывают, являются не только инженерами, но и учеными, поэтому они обычно не используют новейшие компиляторы или даже новейшие версии UNIX / LINUX. Так что, если они делают что-то по старинке, меня это не удивит. - person theJollySin; 02.05.2012
comment
'несколько месяцев` :-) нет проблем с getopt быть молодым или даже зрелым ... вы можете попробовать вытащить getopt источники из ссылок в моем ответе и использовать их. - person alk; 02.05.2012
comment
@Dogbert Это было почти идеальное решение. За исключением того, что меня действительно раздражает попытка запустить библиотеку, которую вы связали (это C ++), с базой кода, которая у меня есть в настоящее время (это C). Я еще не отказался от того, что это будет возможно, но смешение двух языковых разновидностей, похоже, добавляет сложности в сборки Visual Studio. - person theJollySin; 02.05.2012
comment
Я решил отметить ваш ответ как правильный, но здесь была одна деталь, которая вообще уводила нас от использования Visual Studio. Оказывается, Visual Studio допускает только стандарты C89, и у них нет планов поддерживать стандарты C99. Это делает Visual Studio совершенно бесполезной для наших целей. Спасибо за вашу помощь! - person theJollySin; 03.05.2012
comment
Да, я все равно считаю V $ мусором. Eclipse выполняет ту же работу бесплатно и поддерживает последние стандарты. VIM + GCC даже лучше, но для тщательного изучения требуется время. - person Cloud; 03.05.2012
comment
Глупо, как они долгое время игнорировали запросы на поддержку C99. - person ActiveTrayPrntrTagDataStrDrvr; 18.11.2013

getopt() на самом деле очень простая функция. Я сделал для него github gist, код отсюда тоже ниже

#include <string.h>
#include <stdio.h>

int     opterr = 1,             /* if error message should be printed */
  optind = 1,             /* index into parent argv vector */
  optopt,                 /* character checked for validity */
  optreset;               /* reset getopt */
char    *optarg;                /* argument associated with option */

#define BADCH   (int)'?'
#define BADARG  (int)':'
#define EMSG    ""

/*
* getopt --
*      Parse argc/argv argument vector.
*/
int
  getopt(int nargc, char * const nargv[], const char *ostr)
{
  static char *place = EMSG;              /* option letter processing */
  const char *oli;                        /* option letter list index */

  if (optreset || !*place) {              /* update scanning pointer */
    optreset = 0;
    if (optind >= nargc || *(place = nargv[optind]) != '-') {
      place = EMSG;
      return (-1);
    }
    if (place[1] && *++place == '-') {      /* found "--" */
      ++optind;
      place = EMSG;
      return (-1);
    }
  }                                       /* option letter okay? */
  if ((optopt = (int)*place++) == (int)':' ||
    !(oli = strchr(ostr, optopt))) {
      /*
      * if the user didn't specify '-' as an option,
      * assume it means -1.
      */
      if (optopt == (int)'-')
        return (-1);
      if (!*place)
        ++optind;
      if (opterr && *ostr != ':')
        (void)printf("illegal option -- %c\n", optopt);
      return (BADCH);
  }
  if (*++oli != ':') {                    /* don't need argument */
    optarg = NULL;
    if (!*place)
      ++optind;
  }
  else {                                  /* need an argument */
    if (*place)                     /* no white space */
      optarg = place;
    else if (nargc <= ++optind) {   /* no arg */
      place = EMSG;
      if (*ostr == ':')
        return (BADARG);
      if (opterr)
        (void)printf("option requires an argument -- %c\n", optopt);
      return (BADCH);
    }
    else                            /* white space */
      optarg = nargv[optind];
    place = EMSG;
    ++optind;
  }
  return (optopt);                        /* dump back option letter */
}
person bobobobo    schedule 19.06.2013
comment
Я включил это в свой проект, однако, когда я пытаюсь использовать optarg, он говорит, что он не объявлен в Windows. Возвращаемое значение getopt всегда - opt. Как я могу использовать optarg? - person eleijonmarck; 30.01.2015
comment
В заголовочном файле отсутствуют extern char *optarg; и extern int optind, opterr, optopt; - person cbr; 17.01.2017

Есть возможность использовать код из среды исполнения MinGW (от Todd C. Miller):

http://sourceforge.net/apps/trac/mingw-w64/browser/trunk/mingw-w64-crt/misc

Я создал небольшую библиотеку с этими файлами и скриптом CMake (может сгенерировать проект VS):

https://github.com/alex85k/wingetopt

person akks    schedule 10.06.2013
comment
Похоже, ваша библиотека была бы действительно полезной. Я только хотел сказать. Но сначала я увидел комментарий Догберта о Xgetopt, и это помогло. Спасибо хоть! - person theJollySin; 13.09.2013
comment
Спасибо. Это работает, копируйте и вставляйте для быстрого переноса, чтобы использовать программу очень быстро - person namezero; 29.06.2020

Я сделал компиляцию getopt кода под Windows.

Я сделал это, поскольку хотел явно использовать его функции синтаксического анализа командной строки в приложении Windows (командной строке).

Я успешно сделал это, используя VC2010.

Насколько я помню, особых проблем при этом не возникло.

getopt.c getoptl.c

person alk    schedule 01.05.2012
comment
Предлагаемое изменение добавило предложение Обратите внимание, что этот конкретный код подпадает под действие GPLv3, а не LGPL. к этому ответу. Я откатил это назад и включил комментарий здесь. - person Michael Petrotta; 20.08.2012
comment
Эээ, включая getopt.in.h? - person Victor Sergienko; 20.03.2013
comment
@VictorSergienko: Конечно, для компиляции исходников getopt потребовался некоторый код из getopt.in.h. В любом случае, мой ответ не предназначался для понимания того, как компиляция связанных файлов возможна без каких-либо (незначительных) модификаций. Просто скармливать их как есть VC10 не получится. - person alk; 20.03.2013

если вы просто хотите, чтобы getopt использовался в Visual C ++ без других зависимостей, у меня есть портирование getopt.c из последней версии GNU libc 2.12 со всеми новыми функциями. Единственная разница в том, что вам нужно использовать TCHAR вместо char, но это очень обычное дело в окнах.

просто загрузите исходный код, создайте, скопируйте libgetopt.lib и getopt.h getopt_int.h в свой проект.

вы также можете сделать это с помощью CMakeList.txt в корневом каталоге.

загрузить исходный код с github

person bowman han    schedule 09.09.2014

В качестве альтернативы вы можете попробовать использовать glib-2.0. Он был бы немного большим, если бы вам просто понадобился синтаксический анализатор параметров. Положительной стороной будет доступ ко всем остальным замечательным игрушкам в бойком.

Честно говоря, я не пробовал заставить это работать (я в основном придерживаюсь Linux), поэтому YMMV.

Как заставить glib работать в Windows: HowTo < / а>

О, вы могли бы изучить использование mingw для среды сборки и Visual Studio для своей IDE.

Glib для Win32: HowTo

Anywho, надеюсь, это поможет.

person rnordeen    schedule 15.01.2014

Getopt.h существует в git, я его загрузил, и он у меня работает:

https://gist.github.com/ashelly/7776712

person MJBZA    schedule 13.09.2015
comment
Что ж, найти getopt.h не было моей проблемой. Меня больше волновало, что getopt.h Windows работает в среде Linux. Хотя это полезно знать. - person theJollySin; 13.09.2015

Из того, что я читал в документации, заголовочный файл getopt.h относится к библиотеке GNU C, которая используется в Linux (и Hurd). Сама функция getopt стандартизирована POSIX, в котором говорится, что она должна быть объявлена ​​вместе с optind optarg и т. Д. В unistd.h

Я не могу попробовать это в Visual Studio, но стоит проверить, существует ли unistd.h и объявляет ли эта функция, поскольку Visual Studio предоставляет некоторые другие функции POSIX.

Если нет, то я бы определенно взял реализацию getopt, а не переписывал синтаксический анализ аргумента, чтобы он работал без него. Getopt был написан для упрощения работы программиста и большей согласованности для пользователей программ с аргументами командной строки. Однако проверьте лицензию.

person Steven Fosdick    schedule 27.04.2020

Из того, что я помню о getopt.h, все, что он делает, - это удобный синтаксический анализатор для обработки argv из вашей основной функции:

int main(int argc, char * argv[])
{
}

Консольные программы Windows по-прежнему имеют основной метод, поэтому вы можете просто перебрать свой массив argv и самостоятельно проанализировать параметры. например

for ( int i = 1; i < argc; i++ )
{
  if (!strcmp(argv[i], "-f"))
    filename = argv[++i];
}
person Benj    schedule 01.05.2012
comment
Спасибо! Я не уверен, будет ли это для меня практичным. Хотя я понимаю, что могу пролистать ~ 5000 строк кода и переписать эти биты, это код, который мы получаем от других разработчиков. Итак, что произойдет через 2 месяца, когда нам предоставят чуть более новую версию кода? Придется ли мне переделывать код обработки аргументов каждый раз, когда мы получим обновление? На это уходит много времени. - person theJollySin; 02.05.2012
comment
Похоже, вам нужно собраться вместе с этими другими разработчиками и согласовать переносимую систему передачи аргументов. Решение, предоставленное @theJollySin, вполне может быть ответом, но в любом случае написать переносимый анализатор аргументов несложно. - person Benj; 02.05.2012
comment
Со временем API getopt казался мне довольно стабильным. @theJollySin - person alk; 02.05.2012
comment
Зачем делать это вручную, если функция getopt доступна в Интернете? - person bobobobo; 19.06.2013