On Mar 12, 2012, at 12:45 PM, kalth...@googlemail.com wrote:
> Is there a way to determine whether a FreeBSD-system was compiled with gcc or 
> clang?
> I thought of some libs or so that might significantly differ.

It's fairly easy to determine whether assembly code was compiled with gcc or 
clang from idioms they use-- GCC emits .ascii for strings and then adds a 
trailing null; clang uses .asciz, for example.  From that you can also figure 
out whether a particular executable or shared library was compiled with one or 
the other-- gcc is doing a leaf frame caller optimization, where it leave / jmp 
to puts() (using the stack frame allocated for main()), whereas clang is doing 
normal stack frame handling of %rpb and explicit return.

Regards,
-- 
-Chuck

% cat h.c
#include <stdio.h>

int main() {
    puts("Hello, world!\n");
}
% gcc -S -O2 -o h-gcc.s h.c
% clang -S -O2 -o h-clang.s h.c
% cat h-gcc.s
        .cstring
LC0:
        .ascii "Hello, world!\12\0"
        .text
        .align 4,0x90
.globl _main
_main:
LFB3:
        pushq   %rbp
LCFI0:
        movq    %rsp, %rbp
LCFI1:
        leaq    LC0(%rip), %rdi
        leave
        jmp     _puts
LFE3:
        .section 
__TEXT,__eh_frame,coalesced,no_toc+strip_static_syms+live_support
EH_frame1:
        .set L$set$0,LECIE1-LSCIE1
        .long L$set$0
LSCIE1:
        .long   0x0
        .byte   0x1
        .ascii "zR\0"
        .byte   0x1
        .byte   0x78
        .byte   0x10
        .byte   0x1
        .byte   0x10
        .byte   0xc
        .byte   0x7
        .byte   0x8
        .byte   0x90
        .byte   0x1
        .align 3
LECIE1:
.globl _main.eh
_main.eh:
LSFDE1:
        .set L$set$1,LEFDE1-LASFDE1
        .long L$set$1
LASFDE1:
        .long   LASFDE1-EH_frame1
        .quad   LFB3-.
        .set L$set$2,LFE3-LFB3
        .quad L$set$2
        .byte   0x0
        .byte   0x4
        .set L$set$3,LCFI0-LFB3
        .long L$set$3
        .byte   0xe
        .byte   0x10
        .byte   0x86
        .byte   0x2
        .byte   0x4
        .set L$set$4,LCFI1-LCFI0
        .long L$set$4
        .byte   0xd
        .byte   0x6
        .align 3
LEFDE1:
        .subsections_via_symbols

% cat h-clang.s
        .section        __TEXT,__text,regular,pure_instructions
        .globl  _main
        .align  4, 0x90
_main:                                  ## @main
Leh_func_begin0:
## BB#0:
        pushq   %rbp
Ltmp0:
        movq    %rsp, %rbp
Ltmp1:
        leaq    L_.str(%rip), %rdi
        callq   _puts
        xorl    %eax, %eax
        popq    %rbp
        ret
Leh_func_end0:

        .section        __TEXT,__cstring,cstring_literals
L_.str:                                 ## @.str
        .asciz   "Hello, world!\n"

        .section        
__TEXT,__eh_frame,coalesced,no_toc+strip_static_syms+live_support
EH_frame0:
Lsection_eh_frame0:
Leh_frame_common0:
Lset0 = Leh_frame_common_end0-Leh_frame_common_begin0 ## Length of Common 
Information Entry
        .long   Lset0
Leh_frame_common_begin0:
        .long   0                       ## CIE Identifier Tag
        .byte   1                       ## DW_CIE_VERSION
        .asciz   "zR"                   ## CIE Augmentation
        .byte   1                       ## CIE Code Alignment Factor
        .byte   120                     ## CIE Data Alignment Factor
        .byte   16                      ## CIE Return Address Column
        .byte   1                       ## Augmentation Size
        .byte   16                      ## FDE Encoding = pcrel
        .byte   12                      ## DW_CFA_def_cfa
        .byte   7                       ## Register
        .byte   8                       ## Offset
        .byte   144                     ## DW_CFA_offset + Reg (16)
        .byte   1                       ## Offset
        .align  3
Leh_frame_common_end0:
        .globl  _main.eh
_main.eh:
Lset1 = Leh_frame_end0-Leh_frame_begin0 ## Length of Frame Information Entry
        .long   Lset1
Leh_frame_begin0:
Lset2 = Leh_frame_begin0-Leh_frame_common0 ## FDE CIE offset
        .long   Lset2
Ltmp2:                                  ## FDE initial location
        .quad   Leh_func_begin0-Ltmp2
Lset3 = Leh_func_end0-Leh_func_begin0   ## FDE address range
        .quad   Lset3
        .byte   0                       ## Augmentation size
        .byte   4                       ## DW_CFA_advance_loc4
Lset4 = Ltmp0-Leh_func_begin0
        .long   Lset4
        .byte   14                      ## DW_CFA_def_cfa_offset
        .byte   16                      ## Offset
        .byte   134                     ## DW_CFA_offset + Reg (6)
        .byte   2                       ## Offset
        .byte   4                       ## DW_CFA_advance_loc4
Lset5 = Ltmp1-Ltmp0
        .long   Lset5
        .byte   13                      ## DW_CFA_def_cfa_register
        .byte   6                       ## Register
        .align  3
Leh_frame_end0:

.subsections_via_symbols

...and here's a disassembly of main() from gcc:

_main:
0000000100000f10        pushq   %rbp
0000000100000f11        movq    %rsp,%rbp
0000000100000f14        leaq    0x00000039(%rip),%rdi
0000000100000f1b        leave
0000000100000f1c        jmp     0x100000f28     ; symbol stub for: _puts

...and clang:

_main:
0000000100000f10        pushq   %rbp
0000000100000f11        movq    %rsp,%rbp
0000000100000f14        leaq    0x00000039(%rip),%rdi
0000000100000f1b        callq   0x100000f2a     ; symbol stub for: _puts
0000000100000f20        xorl    %eax,%eax
0000000100000f22        popq    %rbp
0000000100000f23        ret

_______________________________________________
freebsd-questions@freebsd.org mailing list
http://lists.freebsd.org/mailman/listinfo/freebsd-questions
To unsubscribe, send any mail to "freebsd-questions-unsubscr...@freebsd.org"

Reply via email to