Формат файла не распознан; обрабатывается как скрипт компоновщика с использованием GCC

#gcc #linker #makefile #compilation

#gcc #компоновщик #makefile #Сборник

Вопрос:

Я довольно новичок в Makefiles и пытаюсь собрать исполняемый файл из 3 файлов: file1.c, file2.c и file1.h в исполняемый файл с именем exFile. Вот что я получил:

 all: exFile
exFile: file1.o file2.o 
    gcc -Wall -g -m32 repeat.o show.o -o repeat

file1.o: file1.c file1.h
    gcc -Wall -g -m32 -S file1.c -o file1.o

file2.o: file2.c 
    gcc -Wall -g -m32 -S file2.c -o file2.o
  

Я искал в Интернете make-файлы в этом формате, но пришел с пустыми руками, поэтому мне было интересно, может ли кто-нибудь помочь. Когда он пытается скомпилироваться, я получаю:

 usr/bin/ld:file1.o:1: file format not recognized; treating as linker script
  

Я компилировал программы, используя файлы ассемблера, но я не уверен, что делать с файлами c или файлом file1.h. file1.c включает file1.h, поэтому я должен связать их (я думаю?). Любые предложения или ссылки на ссылку были бы оценены

Ответ №1:

У вас две проблемы с вашей gcc командной строкой. Во-первых, вы указываете -S флаг, который заставляет gcc выдавать ассемблерный код, а не объектный код. Во-вторых, у вас отсутствует -c флаг, который сообщает gcc скомпилировать файл в объектный файл, но не связать его. Если вы просто удалите -S и больше ничего не измените, в итоге вы получите исполняемую программу с именем file1.o и другую с именем file2.o , а не два объектных файла.

Помимо этих ошибок, вы могли бы упростить свой makefile, используя шаблонные правила. Я предлагаю вам вместо этого попробовать следующее:

 all: exFile
exFile: file1.o file2.o 
    gcc -Wall -g -m32 $^ -o $@

%.o: %.c
    gcc -Wall -g -m32 -c $< -o $@

file1.o: file1.h
  

Или, как указывает EmployedRussian, вы можете выбрать что-то еще более минимальное, что использует больше встроенных функций GNU make:

 CC=gcc
CFLAGS=-Wall -g -m32

all: exFile

exFile: file1.o file2.o 
        $(LINK.c) $^ -o $@

file1.o: file1.h
  

Комментарии:

1. Этот makefile все еще довольно плох. Вам не нужно шаблонное правило — в make оно уже встроено. Кроме того, exFile всегда будет устаревшим, потому что вместо этого вы создаете «repeat». Если вы предоставляете пример того, как исправить makefile, пожалуйста, сделайте это лучше!

2. @Employed Russian: упс, спасибо, что заметили эту опечатку (скопировано из OP). Что касается упрощения makefile, да, это могло бы быть проще, но я не уверен, что это помогло бы пониманию OP, учитывая, что проблемы вызывала не структура makefile.

Ответ №2:

-S Переключение на gcc сообщает ему выводить ассемблер, так что это:

 gcc -Wall -g -m32 -S file1.c -o file1.o
  

Вводит ассемблер в, file1.o но вы хотите, предположительно, скомпилировать file1.c в объектный код:

 gcc -Wall -g -m32 file1.c -o file1.o
  

Когда компоновщик получает ваш, file1.o он сбит с толку, потому что file1.o работает на ассемблере, когда компоновщик ожидает объектный код, отсюда и ваша ошибка.

Поэтому избавьтесь от -S переключателей для file1.o и file2.o .

Комментарии:

1. Спасибо за ответ, но по-прежнему безуспешно … получаю ту же ошибку. Я полностью в тупике по этому поводу. Я изучу это подробнее, я знаю, что я не так уж далек от истины, возможно, просто какую-то деталь я упустил.

2. @user695978: Что произойдет, если вы file file1.o получите тип файла?