User:David-Bryant

From Qt Wiki
Jump to: navigation, search
Triangles oblique.png

Hi. My name is David Bryant. I'm a retired actuary / assembly language (IBM 360 / 370) programmer living in Canyon Lake, Texas. I have been contributing to the KDE project for about three years, mostly doing documentation for the PIM subsystem (KMail, KAddressBook, etc.) I've been struggling to wrap my head around "object-oriented" programs for years. I joined the Qt wiki because I want to understand the c++ code in various KDE programs better than I do now.

Oops is hard!

The other day I encountered a problem while trying to run an example program presented in this article. I think the instructions are a bit unclear. Anyway, I managed to create a compiler error in Qt-Creator that I couldn't circumvent ... the linkage editor was looking for an external symbol "_start" that the c++ compiler had not generated (because I didn't have a "main()" function defined in the source code).

After digging around the internet a little bit, I ran across this snippet of code (compiled with gcc).

 1 #include<stdio.h>
 2 #include<stdlib.h>
 3 void _start()
 4 {
 5     int x = my_fun(); //calling custom main function
 6     exit(x);
 7 }
 8   
 9 int my_fun() // our custom main function
10 {
11     printf("Hello world!/n");
12     return 0;
13 }

If this code is compiled / linked with "gcc -nostartfiles -o example example.c". I get a warning message from the C compiler, but it does create an object program, which looks like this:

example:      file format elf64-x86-64
Disassembly of section .plt:

0000000000001000 <puts@plt-0x10>:
    1000:	ff 35 02 30 00 00    	push   0x3002(%rip)         # 4008 <_GLOBAL_OFFSET_TABLE_+0x8>
    1006:	ff 25 04 30 00 00    	jmp    *0x3004(%rip)        # 4010 <_GLOBAL_OFFSET_TABLE_+0x10>
    100c:	0f 1f 40 00          	nopl   0x0(%rax)

0000000000001010 <puts@plt>:
    1010:	ff 25 02 30 00 00    	jmp    *0x3002(%rip)        # 4018 <puts@GLIBC_2.2.5>
    1016:	68 00 00 00 00       	push   $0x0
    101b:	e9 e0 ff ff ff       	jmp    1000 <puts@plt-0x10>

0000000000001020 <exit@plt>:
    1020:	ff 25 fa 2f 00 00    	jmp    *0x2ffa(%rip)        # 4020 <exit@GLIBC_2.2.5>
    1026:	68 01 00 00 00       	push   $0x1
    102b:	e9 d0 ff ff ff       	jmp    1000 <puts@plt-0x10>

Disassembly of section .text:

0000000000001030 <_start>:
    1030:	55                   	push   %rbp
    1031:	48 89 e5             	mov    %rsp,%rbp
    1034:	48 83 ec 10          	sub    $0x10,%rsp
    1038:	b8 00 00 00 00       	mov    $0x0,%eax
    103d:	e8 0d 00 00 00       	call   104f <my_fun>
    1042:	89 45 fc             	mov    %eax,-0x4(%rbp)
    1045:	8b 45 fc             	mov    -0x4(%rbp),%eax
    1048:	89 c7                	mov    %eax,%edi
    104a:	e8 d1 ff ff ff       	call   1020 <exit@plt>

000000000000104f <my_fun>:
    104f:	55                   	push   %rbp
    1050:	48 89 e5             	mov    %rsp,%rbp
    1053:	48 8d 05 a6 0f 00 00 	lea    0xfa6(%rip),%rax        # 2000 <my_fun+0xfb1>
    105a:	48 89 c7             	mov    %rax,%rdi
    105d:	e8 ae ff ff ff       	call   1010 <puts@plt>
    1062:	b8 00 00 00 00       	mov    $0x0,%eax
    1067:	5d                   	pop    %rbp
    1068:	c3                   	ret

Believe it or not, this actually makes more sense (to me) than the C source code. I can see parameter lists being created, registers being saved and restored, subroutines being called, etc. The only thing I don't see is the literal "Hello World!\n", which is presumably in the object module's data section. I had to dig a little deeper, but I found that, too.

Disassembly of section .rodata:
0000000000002000 <.rodata>:
    2000:	48                   	rex.W
    2001:	65 6c                	gs insb (%dx),%es:(%rdi)
    2003:	6c                   	insb   (%dx),%es:(%rdi)
    2004:	6f                   	outsl  %ds:(%rsi),(%dx)
    2005:	20 77 6f             	and    %dh,0x6f(%rdi)
    2008:	72 6c                	jb     2076 <__GNU_EH_FRAME_HDR+0x66>
    200a:	64 21 00             	and    %eax,%fs:(%rax)

I think this is pretty funny. The "objdump" program is interpreting a bunch of ASCII data as machine instructions! It would make more sense if it displayed like a regular hexdump:

Disassembly of section .rodata:
0000000000002000 <.rodata>:
0002000 6548 6c6c 206f 6f77 6c72 2164 0000 0000    eH ll .o ow lr !d .. ..