Here is an example of a coredump:
(gdb) bt#0 0x08048662 in Xuzhina_dump_c06_s5_ex_child::inheritfrom (char*, Int.) () #1 0x08048609 in Main ()
First look at the Xuzhina_dump_c06_s5_ex_child::inheritfrom assembly:
(GDB) disassemble 0x08048662dump of assembler code for function _zn28xuzhina_dump_c06_s5_ex_child11inheritfromepci:0x0 8048640 <+0>: Push%ebp 0x08048641 <+1>: mov%esp,%ebp 0x08048643 <+3>: Sub $0x1 8,%esp 0x08048646 <+6>: mov 0x8 (%EBP),%eax 0x08048649 <+9>: mov (%EAX),%eax 0x0804864b < ; +11>: mov (%eax),%eax 0x0804864d <+13>: mov 0x8 (%EBP),%edx 0x08048650 <+16>: mov 0xc (%EBP),%ecx 0x08048653 <+19>: mov%ecx,0x4 (%ESP) 0x08048657 <+23>: mov%edx, (%ESP) 0x0804865 A <+26>: Call *%eax 0x0804865c <+28>: mov 0x8 (%EBP),%eax 0x0804865f <+31>: mov 0xc ( %EAX),%eax=> 0x08048662 <+34>: mov (%EAX),%eax 0x08048664 <+36>: mov 0x8 (%EBP),%edx 0x08048 667 <+39>: Lea 0xc (%edx),%ecx 0x0804866a <+42>: mov 0x10 (%EBP),%edx 0x0804866d <+45>: mov%edx,0x4 (%ESP)0x08048671 <+49>: mov%ecx, (%ESP) 0x08048674 <+52>: Call *%eax 0x08048676 <+54>: mov 0x8 (%EBP),%eax 0x08048679 <+57>: Movl $0x1,0x14 (%eax) 0x08048680 <+64>: Leave 0x08048681 < ; +65>: ret End of assembler dump.
By
0x0804865c <+28>: mov 0x8 (%EBP),%eax 0x0804865f <+31>: mov 0xc (%eax),%eax=> 0x08048662 <+34>: mov (%eax),%eax 0x08048664 <+36>: mov 0x8 (%EBP),%edx 0x08048667 <+39>: Lea 0xc (%edx),%ecx 0x0804866a <+42>: mov 0x10 (%EBP),%edx 0x0804866d <+45>: mov %edx,0x4 (%esp) 0x08048671 <+49>: mov %ecx, (%esp ) 0x08048674 <+52>: call *%eax
As you can see, eax is a virtual function table pointer
By the crash command, EAX points to the address is illegal, and eax is by this plus 0xc offset worth, this is placed in ebp+0x8
Take a look at what this is pointing to
(gdb) x/x $ebp +8 0xbff59da0: 0x08c03008 (GDB) x/8x 0x08c030080x8c03008: 0x08048798 0x6c6c6548 0x726f576f 0x6854646c0x8c03018: 0x73497369 0x69766544 0x0000006c 0x00020fe1
Since this address 0x08c03008 the next cell 0x08c0300c and subsequent units each byte is less than 0x80, it is possible that the ASCII code.
And can also be made by
(GDB) I R eaxeax 0x6854646c 1750361196
See the value of eax placed in the 0x8c03014 unit.
See if 0x08c0300c starts with a string:
(GDB) x/s 0x08c0300c0x8c0300c: "Helloworldthisisdevil" (gdb) x/s 0x8c030140x8c03014: "Ldthisisdevil"
Visible, there is indeed a string inside, and this+0xc this virtual function table pointer is exactly the string "Ldthisisdevil". The description is exactly covered by the previous member variable. Why is it covered?
In the Xuzhina_dump_c06_s5_ex!xuzhina_dump_c06_s5_ex_child::inheritfrom function, there are two calls. Take a look at what the previous call is, is it possible to overwrite this virtual function table pointer, If not, let's see if the main function has any other member functions that call this class.
By this section of instructions
0x08048646 <+6>: mov 0x8 (%EBP),%eax 0x08048649 <+9>: mov (%eax),%eax 0X0804864B <+11>: mov (%eax),%eax 0x0804864d <+13>: mov 0x8 (%EBP),%edx 0x08048650 <+16>: mov 0xc (%EBP),%ecx 0x08048653 <+19>: mov %ecx,0x4 (%ESP) 0x08048657 <+23>: mov %edx, (%ESP) 0x0804865a <+26>: call *%eax
As you can see, this function is the first function taken from the first virtual function table.
(gdb) x/x $ebp +8 0xbff59da0: 0x08c03008 (GDB) x/4x 0x08c030080x8c03008: 0x08048798 0x6c6c6548 0x726f576f 0x6854646c (gdb) x/4x 0x080487980x8048798 <_ztv28xuzhina_dump_c06_s5_ex_child+8>: 0x08048614 0x08048640 0xfffffff4 0x08048800
As can be seen from the above, is called the SetName function, there is a parameter. The value of this parameter is passed in Xuzhina_dump_c06_s5_ex_child::inheritfrom by Ebp+c.
Take a look at the contents of Ebp+c:
(gdb) x/x $ebp +0xc0xbff59da4: 0xbff5a672 (GDB) x/s 0xbff5a6720xbff5a672: "Helloworldthisisdevil"
It can be inferred that this function caused the second virtual function table pointer to be rewritten by Xuzhina_dump_c06_s5_ex_father::setname.
Take a look at what Xuzhina_dump_c06_s5_ex_father::setname did:
(GDB) disassemble _zn29xuzhina_dump_c06_s5_ex_father7setnameepcdump of assembler code for function _zn29xuzhina_dump_ C06_S5_EX_FATHER7SETNAMEEPC: 0x08048614 <+0>: push %ebp 0x08048615 <+1>: mov %esp,%ebp 0x08048617 <+3>: Sub $0x18,%esp 0x0804861a <+6>: mov 0x8 (% EBP),%eax 0x0804861d <+9>: Lea 0x4 (%eax),%edx 0x08048620 <+12>: mov 0XC (%EBP),%eax 0x08048623 <+15>: mov %eax,0x4 (%esp) 0x08048627 <+19>: mov %edx, (%ESP) 0x0804862a <+22>: call 0x8048490 <[email protected]> 0x0804862f <+27>: leave 0x08048630 <+28>: ret End of assembler dump.
By reversing the above assembly, you can get this function to be the value of parameter 1 a character Fu copied to the first member variable (THIS+4) of this object. In this coredump, the value of parameter 1 is "Helloworldthisisdevil", the length is 21, Starts with the first parameter, which is (+4). The second virtual function table pointer for this object is located in the +c position, which is overwritten by "Ldthisisdevil".
The source code is as follows:
1 #include <string.h> 2 class Xuzhina_dump_c06_s5_ex_father 3 {4 private:5 char m_name[8]; 6 public:7 virtual void SetName (char* name) 8 {9 strcpy (m_name, name); 10 } 11}; Class Xuzhina_dump_c06_s5_ex_mother (private:16 int m_nature; public:18 virtual void setnature (int nature) {m_nature = nature; 21} 22}; Xuzhina_dump_c06_s5_ex_father class Xuzhina_dump_c06_s5_ex_child:public, public Xuzhina_dump_c06_s5_ex_moth Er, {private:28 int m_sweet; public:30 virtual void Inheritfrom (char* lastName, int na ture) {setName (lastName); setnature (nature); m_sweet = 1; 35 } 36}; 3738 int main (int argc, char* argv[]) 2 (argc <), 43} 44 45 Xuzhina_dump_c06_s5_ex_child* child = new Xuzhina_dump_c06_s5_ex_child; Child->inheritfrom (Argv[1], 1); The return 0; 49}
A study on the principle of Coredump, Linux version x86 6.8, multiple inheritance Coredump example