Re: Bug in i386_process_record?

Hui Zhu
2009-08-24T00:01:02Z

On Mon, Aug 24, 2009 at 07:42, Hui Zhu<teawater@gmail.com> wrote:
> If I am right, this is from the old memory manager -- segment manager.
>  X86 is a old arch and support it.
>
> Now, most of OS include Linux, they don't use this MM, they use page
> manager that X86 support it too (X86 is crazy).  So they set the value
> of segment reg to 0.
>
> For the gdb, the value of segment reg is not the really value.
> cs             0x73     115
> ss             0x7b     123
> ds             0x7b     123
> es             0x7b     123
> fs             0x0      0
> gs             0x33     51
> I have tried some insn that use segment reg such as string ops insn.
> I found that the value of this segment reg cannot affect anything.
>
> And prec just support Linux now.  I have move
> "set_gdbarch_process_record (gdbarch, i386_process_record);" to
> i386-linux-tdep.c.
>
> This patch doesn't add any more thing, just fix the bug.  And this bug
> seems affect a lot of program (for example, Oza's fp example).  I
> suggest let it in first.  After that, we can find a good way to handle
> the segment reg better.
>
> What do you think about it?
>
> Thanks,
> Hui
>
> On Mon, Aug 24, 2009 at 02:24, Eli Zaretskii <eliz@gnu.org> wrote:
>>
>> > From: Hui Zhu <teawater@gmail.com>
>> > Date: Sun, 23 Aug 2009 12:29:33 +0800
>> > Cc: gdb-patches ml <gdb-patches@sourceware.org>
>> >
>> > read_register (I386_ES_REGNUM)
>> > This value is not the value of ES.  This is number of TLB.
>>
>> On what OS?
>

Please let me show a example for it.

cat memrange-reverse.c
/* This testcase is part of GDB, the GNU debugger.

Copyright 2009 Free Software Foundation, Inc.

This program is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3 of the License, or
(at your option) any later version.

This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.

You should have received a copy of the GNU General Public License
along with this program. If not, see <http://www.gnu.org/licenses/>. */

#include <string.h>

#define SIZE_BLOB1 1024
#define SIZE_BLOB2 256

char blob1[SIZE_BLOB1], blob2[SIZE_BLOB2];

int main ()
{
int i;

memset (blob1, 'a', sizeof (blob1));
blob1[sizeof (blob1) - 1] = '\0';

memset (blob2, 'b', sizeof (blob2));
blob2[sizeof (blob2) - 1] = '\0';

for (i = 2; i < 8; i++)
{
memcpy (blob1 + (sizeof (blob1) / i), blob2, sizeof (blob2));
}

return 0; /* end of main */
}

gcc -g memrange-reverse.c

gdb ./a.out
GNU gdb (GDB) 6.8.50.20090807-cvs
Copyright (C) 2009 Free Software Foundation, Inc.
License GPLv3+: GNU GPL version 3 or later <http://gnu.org/licenses/gpl.html>
This is free software: you are free to change and redistribute it.
There is NO WARRANTY, to the extent permitted by law. Type "show copying"
and "show warranty" for details.
This GDB was configured as "i686-pc-linux-gnu".
For bug reporting instructions, please see:
<http://www.gnu.org/software/gdb/bugs/>...
(gdb) start
Temporary breakpoint 1 at 0x80483b5: file memrange-reverse.c, line 29.
Starting program: /home/teawater/Desktop/a.out

Temporary breakpoint 1, main () at memrange-reverse.c:29
29 memset (blob1, 'a', sizeof (blob1));
(gdb) x blob1
0x8049660 <blob1>: 0x00000000
#This address is what we really want to set.

(gdb) b *0xb7eec4e7
Breakpoint 2 at 0xb7eec4e7
(gdb) set disassemble-next-line on
(gdb) c
Continuing.

Breakpoint 2, 0xb7eec4e7 in memset () from /lib/tls/i686/cmov/libc.so.6
0xb7eec4e7 <memset+55>: f3 ab rep stos %eax,%es:(%edi)
#This is the code that will set the blob1

(gdb) disassemble
Dump of assembler code for function memset:
0xb7eec4b0 <memset+0>: cld
0xb7eec4b1 <memset+1>: push %edi
0xb7eec4b2 <memset+2>: mov 0x8(%esp),%edx
0xb7eec4b6 <memset+6>: mov 0x10(%esp),%ecx
0xb7eec4ba <memset+10>: movzbl 0xc(%esp),%eax
0xb7eec4bf <memset+15>: jecxz 0xb7eec4ed <memset+61>
0xb7eec4c1 <memset+17>: mov %edx,%edi
0xb7eec4c3 <memset+19>: and $0x3,%edx
0xb7eec4c6 <memset+22>: je 0xb7eec4d9 <memset+41>
0xb7eec4c8 <memset+24>: jp 0xb7eec4ce <memset+30>
0xb7eec4ca <memset+26>: stos %al,%es:(%edi)
0xb7eec4cb <memset+27>: dec %ecx
0xb7eec4cc <memset+28>: je 0xb7eec4ed <memset+61>
0xb7eec4ce <memset+30>: stos %al,%es:(%edi)
0xb7eec4cf <memset+31>: dec %ecx
0xb7eec4d0 <memset+32>: je 0xb7eec4ed <memset+61>
0xb7eec4d2 <memset+34>: xor $0x1,%edx
0xb7eec4d5 <memset+37>: jne 0xb7eec4d9 <memset+41>
0xb7eec4d7 <memset+39>: stos %al,%es:(%edi)
0xb7eec4d8 <memset+40>: dec %ecx
0xb7eec4d9 <memset+41>: mov %ecx,%edx
0xb7eec4db <memset+43>: shr $0x2,%ecx
0xb7eec4de <memset+46>: and $0x3,%edx
0xb7eec4e1 <memset+49>: imul $0x1010101,%eax,%eax
0xb7eec4e7 <memset+55>: rep stos %eax,%es:(%edi)
0xb7eec4e9 <memset+57>: mov %edx,%ecx
0xb7eec4eb <memset+59>: rep stos %al,%es:(%edi)
0xb7eec4ed <memset+61>: mov 0x8(%esp),%eax
0xb7eec4f1 <memset+65>: pop %edi
0xb7eec4f2 <memset+66>: ret
End of assembler dump.
(gdb) info reg $edi
edi 0x8049660 134518368
(gdb) info reg $es
es 0x7b 123

#rep stos %eax,%es:(%edi)
$edi + 0 = 0x8049660 blob1
$edi + $es != 0x8049660 blob1

Thanks,
Hui