When encountering the error bash: ./myfile: cannot execute binary file
, the file
command reveals crucial information:
$ file myfile
myfile: ELF 64-bit LSB relocatable, x86-64, version 1 (SYSV), not stripped
The key term here is "relocatable" - this indicates the file is an object file (.o) rather than a complete executable. Object files contain machine code but aren't directly executable by the OS.
ELF (Executable and Linkable Format) files come in three primary types:
- Relocatable (.o files): Intermediate compilation output
- Executable: Complete programs ready to run
- Shared object (.so files): Dynamic libraries
To confirm this is indeed an object file, examine the ELF headers:
$ readelf -h myfile
ELF Header:
Magic: 7f 45 4c 46 02 01 01 00 00 00 00 00 00 00 00 00
Class: ELF64
Data: 2's complement, little endian
Version: 1 (current)
OS/ABI: UNIX - System V
ABI Version: 0
Type: REL (Relocatable file)
Machine: Advanced Micro Devices X86-64
Version: 0x1
Entry point address: 0x0
Start of program headers: 0 (bytes into file)
Start of section headers: 488 (bytes into file)
Flags: 0x0
Size of this header: 64 (bytes)
Size of program headers: 0 (bytes)
Number of program headers: 0
Size of section headers: 64 (bytes)
Number of section headers: 13
Section header string table index: 10
The user likely stopped after the compilation phase without linking. Here's the complete process:
# Single source file compilation
gcc -c myfile.c -o myfile.o # Creates relocatable object
gcc myfile.o -o myfile # Creates executable
# Alternative single-step compilation
gcc myfile.c -o myfile # Combines compilation and linking
For more complex scenarios, these commands help identify issues:
# Check for missing linker symbols (if partially linked)
nm -C myfile
# Verify dynamic dependencies (for executables)
ldd myfile_executable
# Disassemble object code
objdump -d myfile.o
# Compare with known working executable
file /bin/ls
Case 1: Accidentally distributing .o files instead of executables
# Solution: Rebuild properly
make clean
make
Case 2: Cross-compilation architecture mismatch
# Verify architecture match
file myfile
uname -m
Case 3: Missing linker step in build scripts
# Ensure build system includes linking phase
gcc $(OBJECT_FILES) -o $@
Modern build systems handle these phases automatically. For example in Make:
# Sample Makefile
CC = gcc
CFLAGS = -Wall -O2
myapp: myfile.o utils.o
$(CC) $(CFLAGS) -o $@ $^
%.o: %.c
$(CC) $(CFLAGS) -c $< -o $@
This ensures proper separation of compilation and linking phases while maintaining correct file types.
When encountering the error bash: ./myfile: cannot execute binary file
, we're dealing with a fundamental mismatch between the file type and execution requirements. The file
command reveals critical information:
$ file myfile
myfile: ELF 64-bit LSB relocatable, x86-64, version 1 (SYSV), not stripped
The key identifier here is "relocatable" in the ELF header. Unlike executable files, relocatable objects (.o files) are intermediate compilation outputs not designed for direct execution. They require linking to become complete executables.
Compare these two outputs:
# Typical executable output
$ file /bin/ls
/bin/ls: ELF 64-bit LSB executable, x86-64, version 1 (SYSV), dynamically linked
# Your problematic file
$ file myfile
myfile: ELF 64-bit LSB relocatable, x86-64, version 1 (SYSV), not stripped
The readelf
output confirms this diagnosis. Notice the missing program header table (required for executables) and the presence of relocation sections:
$ readelf -h myfile | grep Type
Type: REL (Relocatable file)
Here are the technical approaches to resolve this:
Option 1: Proper Compilation and Linking
If you have source code available, ensure proper compilation:
# For C programs
gcc -c source.c -o object.o # Creates relocatable object
gcc object.o -o executable # Creates proper executable
# Verify with:
file executable
Option 2: Identifying Missing Steps
Common compilation mistakes that lead to this situation:
# Missing linking step (wrong)
gcc -c program.c -o program
# Correct complete compilation
gcc program.c -o program
Advanced Verification Techniques
For deeper analysis, examine the ELF structure:
# Check for program headers (missing in relocatable objects)
readelf -l myfile
# View symbol table
readelf -s myfile
# Disassemble code
objdump -d myfile
When communicating with the user who provided the binary, you should explain:
- The file is an intermediate compilation product, not a complete executable
- They likely used
gcc -c
without final linking - The solution requires recompilation with proper linking
To avoid this in development environments:
# Use makefile rules that ensure complete compilation
all: program
program: program.o
$(CC) $^ -o $@
program.o: program.c
$(CC) -c $< -o $@