i386 GNU ld: file not recognized: File format not recognized - c

I'm working my way through The Little Book About OS Development, specifically the section on the framebuffer (linked). I'm able to successfully assemble, link, turn into an ISO file and boot pure assembly, but as soon as I try to link a compiled object file for my C code (called from my loader, which was written in assembly), the linker complains. Here's the output:
nasm -f elf loader.s -o loader.o
nasm -f elf out.s -o out.o
/usr/local/Cellar/gcc#6/6.4.0/bin/gcc-6 -m32 -nostdlib -nostdinc -fno-builtin -fno-stack-protector -nostartfiles -nodefaultlibs -Wall -Wextra -Werror -c framebuffer.c -o framebuffer.o
/usr/local/Cellar/gcc#6/6.4.0/bin/gcc-6 -m32 -nostdlib -nostdinc -fno-builtin -fno-stack-protector -nostartfiles -nodefaultlibs -Wall -Wextra -Werror -c kmain.c -o kmain.o
i386-unknown-linux-gnu-ld -T link.ld -melf_i386 loader.o out.o framebuffer.o kmain.o -o kernel.elf
framebuffer.o: file not recognized: File format not recognized
make: *** [kernel.elf] Error 1
I'm on a Mac, so as you can tell I've compiled a custom version of the GNU linker so that I can use linker scripts, and I've made sure to specify GCC 6 (the system default is 4.0). Anyway, here's my Makefile:
OBJECTS = loader.o out.o framebuffer.o kmain.o
CC = /usr/local/Cellar/gcc#6/6.4.0/bin/gcc-6
CFLAGS = -m32 -nostdlib -nostdinc -fno-builtin -fno-stack-protector \
-nostartfiles -nodefaultlibs -Wall -Wextra -Werror -c
LDFLAGS = -T link.ld -melf_i386
AS = nasm
ASFLAGS = -f elf
all: kernel.elf
kernel.elf: $(OBJECTS)
i386-unknown-linux-gnu-ld $(LDFLAGS) $(OBJECTS) -o kernel.elf
os.iso: kernel.elf
cp kernel.elf iso/boot/kernel.elf
mkisofs -R \
-b boot/grub/stage2_eltorito \
-no-emul-boot \
-boot-load-size 4 \
-A os \
-input-charset utf8 \
-quiet \
-boot-info-table \
-o os.iso \
iso
run: os.iso
bochs -f bochsrc.txt -q
%.o: %.c
$(CC) $(CFLAGS) $< -o $#
%.o: %.s
$(AS) $(ASFLAGS) $< -o $#
clean:
rm -rf *.o kernel.elf os.iso
Here's my linker script:
ENTRY(loader) /* the name of the entry label */
SECTIONS {
. = 0x00100000; /* the code should be loaded at 1 MB */
.text ALIGN (0x1000) : /* align at 4 KB */
{
*(.text) /* all text sections from all files */
}
.rodata ALIGN (0x1000) : /* align at 4 KB */
{
*(.rodata*) /* all read-only data sections from all files */
}
.data ALIGN (0x1000) : /* align at 4 KB */
{
*(.data) /* all data sections from all files */
}
.bss ALIGN (0x1000) : /* align at 4 KB */
{
*(COMMON) /* all COMMON sections from all files */
*(.bss) /* all bss sections from all files */
}
}
Any help would be appreciated.

As it turns out, this was solved by cross-compiling GNU Binutils and GCC together (with the same prefix) on my Mac. I did this according to the instructions here.

Related

Why does SystemTable->ConIn functions cause my fans to go insane and freeze the booting process?

So basically, I'm trying to do input with gnu-efi and I've struggled but I finally got something compiling. Here it is:
#include <efi.h>
#include <efilib.h>
EFI_STATUS EFIAPI efi_main (EFI_HANDLE ImageHandle, EFI_SYSTEM_TABLE *SystemTable) {
EFI_STATUS status;
EFI_INPUT_KEY Key;
InitializeLib(ImageHandle, SystemTable);
//status = SystemTable->ConIn->Reset(SystemTable->ConIn, FALSE);
if (EFI_ERROR(status))
return status;
SystemTable->ConOut->OutputString(SystemTable->ConOut, L"Hello pussy\n");
while((status = SystemTable->ConIn->ReadKeyStroke(SystemTable->ConIn, &Key)) == EFI_NOT_READY && Key.ScanCode != 0x17);
times
return EFI_SUCCESS;
}
My problem is that this causes the process to be stuck on the starting and makes my fans go crazy. There are no errors or anything. It just doesn't work. It stops the process and it makes my fans go overdrive. Any ConIn function does that.
**
Extra info:
**
The make file I compile my code with:
OBJS = main3.o
TARGET = hello3.efi
EFIINC = /usr/include/efi
EFIINCS = -I$(EFIINC) -I$(EFIINC)/$(ARCH) -I$(EFIINC)/protocol
LIB = /usr/lib64
EFILIB = /usr/lib64/
EFI_CRT_OBJS = $(EFILIB)/crt0-efi-$(ARCH).o
EFI_LDS = $(EFILIB)/elf_$(ARCH)_efi.lds
CFLAGS = -ffreestanding $(EFIINCS) -fno-stack-protector -fpic \
-fshort-wchar -mno-red-zone -Wall -c
ifeq ($(ARCH),x86_64)
CFLAGS += -DEFI_FUNCTION_WRAPPER
endif
LDFLAGS = -nostdlib -znocombreloc -T $(EFI_LDS) -shared \
-Bsymbolic -L $(EFILIB) -L $(LIB) $(EFI_CRT_OBJS)
all: $(TARGET)
main3.o: hello.c
gcc $(CFLAGS) hello3.c -o main3.o
hello3.so: $(OBJS)
ld $(LDFLAGS) $(OBJS) -o $# -lefi -lgnuefi
%.efi: %.so
objcopy -j .text -j .sdata -j .data -j .dynamic \
-j .dynsym -j .rel -j .rela -j .reloc \
--target=efi-app-$(ARCH) $^ $#
the command I run qemu with:
qemu-system-x86_64 -bios OVMF.fd -drive media=disk,id=boot,format=raw,file=fat:rw:DirContainingEFI/BOOT/bootx64.efi,index=0

"undefined reference" error compiling a static library in C

I have a file main.c, a header rippledp.h and a library rippledp.a. The problem is: when I execute the "make" command, I get this output:
g++ -O2 -DNDEBUG -static -o rippledp main.o rippledp.a -lm -pthread
main.o: In function `main':
main.c:(.text+0x24): undefined reference to `rippledp_read'
main.c:(.text+0x39): undefined reference to `rippledp'
main.c:(.text+0x43): undefined reference to `rippledp_write'
collect2: ld returned 1 exit status
make: ** [rippledp] Erro 1
Here is the Makefile:
#--------------------------------------------------#
# Ripple-DP (ISPD2015 contest version) #
# Copyright (c) 2015 #
# Department of Computer Science and Engineering #
# The Chinese Univeristy of Hong Kong #
# #
# Contact: #
# Wing-Kai Chow <wkchow#cse.cuhk.edu.hk> #
# Evangeline F.Y. Young <fyyoung#cse.cuhk.edu.hk> #
#--------------------------------------------------#
OPT= -O2 -DNDEBUG
#OPT= -O0 -ggdb
TYPE= -static
#WFLAG= -Wall -Winline
CC= g++ $(OPT) $(TYPE) $(WFLAG) $(DEBUG)
LIBS= -lm -pthread
SRCS = ${OBJS:%.o=%.c}
BFILE = rippledp
all: $(BFILE)
#$(BFILE): main.o rippledp.a libdef.a liblef.a
# $(CC) -o $(BFILE) main.o rippledp.a libdef.a liblef.a $(LIBS)
$(BFILE): main.o rippledp.a
$(CC) -o $(BFILE) main.o rippledp.a $(LIBS)
%.o : %.c %.h
$(CC) -c $*.c
clean:
rm -f *.o $(BFILE) core
Here is main.c:
#include "rippledp.h"
int main(int argc, char **argv){
/* read benchmark files: tech.lef, cells.lef, floorplan.def */
/* read global placement solution: placed.def */
rippledp_read((char*) "tech.lef", (char*) "cells.lef", (char*) "floorplan.def", (char*) "placed.def");
/* detailed placement with target utility and maximum displacement constraint */
rippledp(0.8, 200000);
/* write the detailed placement solution to output file */
rippledp_write((char*)"dplaced.def");
return 0;
}
And here is rippledp.h:
/*--------------------------------------------------*/
/* Ripple-DP (ISPD2014 contest version) */
/* Copyright (c) 2014 */
/* Department of Computer Science and Engineering */
/* The Chinese Univeristy of Hong Kong */
/* */
/* Contact: */
/* Wing-Kai Chow <wkchow#cse.cuhk.edu.hk> */
/* Evangeline F.Y. Young <fyyoung#cse.cuhk.edu.hk> */
/*--------------------------------------------------*/
#ifndef _RIPPLEDP_H_
#define _RIPPLEDP_H_
/*read benchmarks and placed global placement solution*/
void rippledp_read(char *tech_file, char *cell_file, char *floorplan_file, char *placed_file);
/*Perform displacement-constrained legalization and detailed placement*/
/* target_util = target utility */
/* max_disp = maximum displacement constraint */
void rippledp(double target_util, double max_disp);
/*write placement result in DEF format*/
void rippledp_write(char *output_file);
#endif
I also tried to compile and link manually. I first compiled using:
gcc -c main.c
Then, I tried all these alternatives for linking (I renamed rippledp.a to librippledp.a):
gcc -o out -L. -lrippledp main.o
gcc -o out -L. main.o -lrippledp
gcc -o out main.o -L. -lrippledp
gcc main.o -o out -L. -lrippledp
gcc -o out -lrippledp -L. main.o
gcc -lrippledp -o out -L. main.o
and the output was the same.
I dont have access to the library content.
Your library is compiled with C++ and thus contains C++ mangled names. But you compiled main.c as C, so it looked for unmangled names and thus couldn't find them. Rename main.c to main.cpp and compile it with g++ to fix this issue.

Getting "collect2: error: ld returned 1 exit status" in C

This is my Makefile for the compiler.
CC = arm-none-eabi-gcc
AS = arm-none-eabi-as
LD = arm-none-eabi-ld
OD = arm-none-eabi-objdump
CFLAGS = -g -c -O1 -mcpu=cortex-m0 -mthumb
AFLAGS = -g -c -mcpu=cortex-m0 -mthumb
LDFLAGS = -g -mcpu=cortex-m0 -mthumb --specs=rdimon.specs -lc -lrdimon
ODFLAGS = -d
all: HW1.elf
test: HW1.elf
# echo "...copying"
qemu-system-arm -machine versatilepb -cpu cortex-m3 -nographic -monitor null -serial null -semihosting -k\
ernel HW1.elf
HW1.elf: test.o t1.o
$(CC) $(LDFLAGS) test.o t1.o -o HW1.elf
test.o: test.c t1.o
# echo ".compiling"
$(CC) $(CFLAGS) test.c t1.o -o test.o
t1.o: t1.s
# echo ".assembling"
$(AS) $(AFLAGS) t1.s -o t1.o
clean:
rm -rf t1.o test.o HW1.elf
When I do make all, I get
.assembling
arm-none-eabi-as -g -c -mcpu=cortex-m0 -mthumb t1.s -o t1.o
.compiling
arm-none-eabi-gcc -g -c -O1 -mcpu=cortex-m0 -mthumb test.c t1.o -o test.o
arm-none-eabi-gcc: warning: t1.o: linker input file unused because linking not done
arm-none-eabi-ld -g -mcpu=cortex-m0 -mthumb --specs=rdimon.specs -lc -lrdimon test.o -o HW1.elf
arm-none-eabi-ld: unrecognised emulation mode: thumb
Supported emulations: armelf
make: *** [HW1.elf] Error 1
I have looked at numberous collect2 errors on StackOverflow and find that there is a function either not defined or is mislabeled.
I have entered the directory in the ~/.bashrc file to call arm-none-eabi library functions. I know that the error has nothing to do with the t1.s and/or test.c files and solely to do with an improper notation dealing with my makefile, but I'm lost as to what I'm doing wrong. I know it's something with test.o.
I will provide test.c and t1.s just in case there is something wrong with them.
test.c
include <stdio.h>
extern int inc(int);
#define RED_COUNT 5
#define YELLOW_COUNT 2
#define GREEN_COUNT 5
enum light_states {RED, YELLOW, GREEN};
static int state = RED;
void stop_light () {
static int state_counter = 0;
switch (state) {
case RED:
printf("RED\n");
if (++state_counter >= RED_COUNT) {
state_counter = 0;
state = GREEN;
}
break;
case GREEN:
printf("GREEN\n");
if (++state_counter >= GREEN_COUNT) {
state_counter = 0;
state = YELLOW;
}
break;
case YELLOW:
printf("YELLOW\n");
if (++state_counter >= YELLOW_COUNT) {
state_counter = 0;
state = RED;
}
break;
default:
state = RED;
state_counter = 0;
break;
}
}
main(){
int i;
while (i < 36) {
stop_light();
i = inc(i);
}
}
t1.s
.text
.syntax unified
.thumb
.global inc
.type inc, %function
inc:
adds r0,r0,#1
bx lr
EDIT 1:
Updated the missing '-c' and am now getting a new error regarding LD.
EDIT 2:
Updated the LD error. Everything fixed now and answers were very helpful!

What library to include to prevent "Undefined reference to '_exit'" ? What is newlib?

Based on the Limifrog STM32L board examples, I am trying to setup my own toolchain for ARM development (STM32F40x based).
I get an error:
C:\Users\pmu\embedded\empty_stm32>make
arm-none-eabi-gcc -mthumb -mcpu=cortex-m4 -mfloat-abi=hard -mfpu=fpv4-sp-d16 -I
./inc -I./../Libraries/CMSIS/Device/ST/STM32F4xx/Include -I./../Libraries/CMSIS/
Include -Os -Wall -ffunction-sections -fdata-sections -fno-exceptions -Wno-write
-strings -o main src/main.c
c:/program files (x86)/gnu tools arm embedded/4.9 2015q3/bin/../lib/gcc/arm-none
-eabi/4.9.3/../../../../arm-none-eabi/lib/armv7e-m/fpu\libc.a(lib_a-exit.o): In
function `exit':
exit.c:(.text.exit+0x16): undefined reference to `_exit'
collect2.exe: error: ld returned 1 exit status
make: *** [main] Error 1
when compiling:
#include "My_Globals.h"
int main(void) {
while(1) {
}
return 0;
}
What does this error mean? Why does it not occur in the Board examples above?
The Makefile
# Compilation Tools
CC = arm-none-eabi-gcc
LD = arm-none-eabi-ld
CP = arm-none-eabi-objcopy
OD = arm-none-eabi-objdump
SIZE = arm-none-eabi-size
# Optimization (ß,1,2,s)
OPT = s
ROOT = ./..
CMSIS_DIR = $(ROOT)/Libraries/CMSIS
HAL_DIR = $(ROOT)/Libraries/CMSIS/Include
SRC = ./src
INC_LOCAL = ./inc
INCLUDES = \
$(INC_LOCAL) \
$(CMSIS_DIR)/Device/ST/STM32F4xx/Include \
$(CMSIS_DIR)/Include
ARCH_FLAGS = -mthumb -mcpu=cortex-m4 -mfloat-abi=hard -mfpu=fpv4-sp-d16
LD_FLAGS =
# Compiler flags
CFLAGS = \
$(ARCH_FLAGS) \
$(addprefix -I,$(INCLUDES)) \
-O$(OPT) \
-Wall \
-ffunction-sections \
-fdata-sections \
-fno-exceptions \
-Wno-write-strings
main:
#echo "start"
#echo $#
$(CC) $(LDFLAGS) $(CFLAGS) -o $# src/main.c
Now, what libraries can be used to re-use the implementation of _exit() from elsewhere?

Trying to use matlab's libmat.dll, but the compiler doesn't recognize the function from the library

I am trying to use matlab libmat.dll in a C application. To compile my C application I use MinGW, for now I use matlab exemple "matcreate.c" and try to compile it, so the projects consist of only one file : main.c .
Here is the makefile I use :
MATINCLUDE = "C:\Program Files\MATLAB\R2010a\extern\include"
MATLIBRARY = "C:\Program Files\MATLAB\R2010a\bin\win64"
#
CC = gcc
LD = gcc
CFLAGS = -O3 -Wall
LFLAGS = -Wall -O3
LIBS = -I$(MATINCLUDE) -L$(MATLIBRARY)
#
PROG = matTest
LISTEOBJ = \
main.o
.c.o :
$(CC) -c $(CFLAGS) $(LIBS) -o $# $<
all : $(PROG)
$(PROG) : $(LISTEOBJ)
$(LD) -o $(PROG) $(LFLAGS) $(LISTEOBJ) $(LIBS)
clean :
rm -f *.obj
Here is what I get in the console
E:\Users\Desk\Dropbox\matTest>make
gcc -c -O3 -Wall -I"C:\Program Files\MATLAB\R2010a\extern\include" -L"C:\Pr
ogram Files\MATLAB\R2010a\bin\win64" -o main.o main.c
gcc -o Hello_world -Wall -O3 main.o -I"C:\Program Files\MATLAB\R2010a\extern\i
nclude" -L"C:\Program Files\MATLAB\R2010a\bin\win64"
main.o:main.c:(.text.startup+0x48): undefined reference to `matOpen'
main.o:main.c:(.text.startup+0x6e): undefined reference to `mxCreateDoubleMatrix
_730'
e:/mingw/bin/../lib/gcc/mingw32/4.8.1/../../../../mingw32/bin/ld.exe: main.o: ba
d reloc address 0x6e in section `.text.startup'
e:/mingw/bin/../lib/gcc/mingw32/4.8.1/../../../../mingw32/bin/ld.exe: final link
failed: Invalid operation
collect2.exe: error: ld returned 1 exit status
make: *** [Hello_world] Error 1
Why do I have "undefined reference to matOpen'" and "undefined reference to mxCreateDoubleMatrix" ?? those function are declared in mat.h. and I added #include "mat.h" to the begining of main.c
thank you
Looks like you have included the path to the matlab library, but not the library itself. You need to add a -l<libraryname> to your link line.

Resources