Вы хотите разделить две вещи
- Сборка SCIP
- Сборка и связывание вашей программы.
Сборка SCIP
Обычно можно было бы go узнать об этой библиотеке и установить ее с помощью менеджера пакетов в большинстве UNIX -подобных систем или сделать make install
, чтобы скопировать ее в систему. Затем заголовочные файлы et c. будет автоматически найден. Если вы не хотите делать это, а скорее «связываете» SCIP с вашей программой, вы обычно распространяете копию или связываете копию этой версии для вашей программы (копию кода в вашем исходном дереве, например, в разделе «external» или используя git подмодулей, ...). В любом случае, однако, вы не хотите, чтобы путь к SCIP был абсолютным. В качестве примера используйте этот макет:
./
-- external/SCIP
-- cmain.c
-- Makefile
В Makefile вы можете установить SCIPDIR как это для последующего использования:
SCIPDIR := "./external/SCIP"
Сначала, однако, вы должны понимать, как строить вручную. Для этого вы вводите «./external/SCIP» и собираете библиотеку в соответствии с инструкциями в файле Readme (часто делая что-то вроде ./configure && make && make install
). Если вы хотите автоматизировать это, вы можете сделать это из вашего основного файла. Для этого вы можете добавить «фальшивую» цель (ie. Цель, которая не будет точно создавать один вывод, но создаст все зависимости), которую мы будем называть dep
:
dep:
cd $(SCIPDIR); ./configure
$(MAKE) -C $(SCIPDIR)
.PHONY: dep
( спасибо @UpAndAdam за указание на то, что вы должны изменить CWD перед запуском скрипта configure)
Для этого мы рекурсивно вызываем make для нашего подпроекта. Мы не хотим устанавливать файлы в масштабе всей системы, поэтому мы просто собираем библиотеку.
Сборка вашей программы
Теперь мы добавим два правила-шаблона, которые определяют, как создавать и связывать C программы. GNU / Make (тот, который вы используете) уже имеет встроенные суффиксные правила, но он уже по умолчанию знает, как создавать C программы, но с суффиксными правилами сложно разобраться, и вы уже используете другие функции GNU / Make, поэтому мы также можем использовать шаблонные правила, которые примерно эквивалентны, и отключить встроенные правила:
%.o: %.c
$(CC) $(CPPFLAGS) $(CFLAGS) -c -o $@ $<
%: %.o
$(CC) $(LDFLAGS) $(CFLAGS) -o $@ $^ $(LDLIBS)
.SUFFIXES:
Небольшое замечание: мы компилируем один объектный файл из одного c файла путем сопоставления с шаблоном. Я использовал стандартные переменные, CPPFLAGS (препроцессор C, а не C ++!), CFLAGS (флаги компилятора и функций C) и перечислил все опции перед аргументом без опции $<
, который будет содержать (первую) указанную зависимость например "CMain. c". Не все C компиляторы допускают смешивание опций и аргументов.
Для линковки я делаю то же самое, но я перечисляю библиотеки, с которыми мы хотим связать последнюю. Это важно, компилятор classi c C будет отбрасывать любые библиотеки, перечисленные там, если в списке не было ранее объектов, зависящих от этой переменной.
Теперь, когда мы знаем, как построить Программа generi c C, мы на самом деле хотим сначала собрать SCIP, затем вашу программу и связать ее. Для этого мы создадим новую зависимость PHONY под названием «all», которая будет делать именно это:
all: dep cmain
.PHONY: dep all
Однако, если мы сейчас выполним make all
, она потерпит неудачу, поскольку мы еще не сделали указал путь включения et c. Для этого мы установили переменные, которые мы использовали ранее, на необходимые значения (я угадал указанный путь c, так как я на мобильном телефоне):
CPPFLAGS += -I$(SCIPDIR)/include
LDFLAGS += -L$(SCIPDIR)
LDLIBS += -lscip
Собираем все вместе
Теперь это должно работать, более или менее. Одна вещь заключается в том, что в качестве цели по умолчанию обычно используется all
, то есть первая цель, указанная в файле Makefile. Итак, мы пишем:
CPPFLAGS += -I$(SCIPDIR)/include
LDFLAGS += -L$(SCIPDIR)
LDLIBS += -lscip
all: dep cmain
%.o: %.c
$(CC) $(CPPFLAGS) $(CFLAGS) -c -o $@ $<
%: %.o
$(CC) $(LDFLAGS) $(CFLAGS) -o $@ $^ $(LDLIBS)
dep:
cd $(SCIPDIR); ./configure.sh
$(MAKE) -C $(SCIPDIR)
.PHONY: dep all
.SUFFIXES:
Примечание: я на мобильном телефоне, поэтому я не смог проверить и не знаю точных путей, но это должно вас сопровождать. Также мой код здесь использовал пробелы вместо вкладок в Makefile по той же причине. Обязательно замените их.