public inbox for gdb-prs@sourceware.org
help / color / mirror / Atom feed
* [Bug exp/30817] New: [gdb/exp] Different interpretation of print options between C and Fortran
@ 2023-09-01 11:22 vries at gcc dot gnu.org
  2023-09-14 18:34 ` [Bug exp/30817] " cvs-commit at gcc dot gnu.org
  0 siblings, 1 reply; 2+ messages in thread
From: vries at gcc dot gnu.org @ 2023-09-01 11:22 UTC (permalink / raw)
  To: gdb-prs

https://sourceware.org/bugzilla/show_bug.cgi?id=30817

            Bug ID: 30817
           Summary: [gdb/exp] Different interpretation of print options
                    between C and Fortran
           Product: gdb
           Version: HEAD
            Status: NEW
          Severity: normal
          Priority: P2
         Component: exp
          Assignee: unassigned at sourceware dot org
          Reporter: vries at gcc dot gnu.org
  Target Milestone: ---

I wrote a fortran variant of gdb.base/huge.c:
...
$ cat test.f90
program arrays
  implicit none

  integer, dimension(2 * 1024 * 1024) :: array1
  print *, 'Hello, World!', array1(1)
end program arrays
$ gfortran test.f90 -g
...

For the gdb.base/huge.exp executable I used this:
...
$ gdb -q -batch outputs/gdb.base/huge/huge -ex start -ex "set max-value-size
unlimited" -ex "print a"
Temporary breakpoint 1 at 0x40053b: file
/data/vries/gdb/src/gdb/testsuite/gdb.base/huge.c, line 18.

Temporary breakpoint 1, main () at
/data/vries/gdb/src/gdb/testsuite/gdb.base/huge.c:18
18        memcpy (a, b, sizeof (a));
$1 = {0 <repeats 2097152 times>}
...
so I tried the same but got a different output:
...
$ gdb -q a.out -ex start -ex "set max-value-size unlimited" -ex "print array1"
Reading symbols from a.out...
Temporary breakpoint 1 at 0x400772: file test.f90, line 5.
Starting program: /data/vries/gdb/a.out 

Temporary breakpoint 1, arrays () at test.f90:5
5         print *, 'Hello, World!', array1(1)
$1 = (0, <repeats 200 times>, ...)
...

Apparently there is a different interpretation of print settings.

After adding "print elements unlimited", I get the same:
...
$ gdb -q -batch a.out -ex start -ex "set max-value-size unlimited" -ex "set
print elements unlimited" -ex "print array1"
Temporary breakpoint 1 at 0x400772: file test.f90, line 5.

Temporary breakpoint 1, arrays () at test.f90:5
5         print *, 'Hello, World!', array1(1)
$1 = (0, <repeats 2097152 times>)
...

The documentation says (
https://sourceware.org/gdb/onlinedocs/gdb/Print-Settings.html ):
...
set print elements number-of-elements
set print elements unlimited

    Set a limit on how many elements of an array GDB will print. If GDB is
printing a large array, it stops printing after it has printed the number of
elements set by the set print elements command. This limit also applies to the
display of strings. When GDB starts, this limit is set to 200. Setting
number-of-elements to unlimited or zero means that the number of elements to
print is unlimited.
...
so I guess this is indeed multi-interpretable.

My understanding of this is that this print setting tries to prevent printing a
lot, so I think the C behaviour makes more sense.

-- 
You are receiving this mail because:
You are on the CC list for the bug.

^ permalink raw reply	[flat|nested] 2+ messages in thread

* [Bug exp/30817] [gdb/exp] Different interpretation of print options between C and Fortran
  2023-09-01 11:22 [Bug exp/30817] New: [gdb/exp] Different interpretation of print options between C and Fortran vries at gcc dot gnu.org
@ 2023-09-14 18:34 ` cvs-commit at gcc dot gnu.org
  0 siblings, 0 replies; 2+ messages in thread
From: cvs-commit at gcc dot gnu.org @ 2023-09-14 18:34 UTC (permalink / raw)
  To: gdb-prs

https://sourceware.org/bugzilla/show_bug.cgi?id=30817

--- Comment #1 from cvs-commit at gcc dot gnu.org <cvs-commit at gcc dot gnu.org> ---
The master branch has been updated by Tom de Vries <vries@sourceware.org>:

https://sourceware.org/git/gitweb.cgi?p=binutils-gdb.git;h=265687478be8b9ca7e54d5eca1277a7853c36a0a

commit 265687478be8b9ca7e54d5eca1277a7853c36a0a
Author: Tom de Vries <tdevries@suse.de>
Date:   Thu Sep 14 20:34:00 2023 +0200

    [gdb/exp] Clean up asap in value_print_array_elements

    I've been running the test-suite on an i686-linux laptop with 1GB of
memory,
    and 1 GB of swap, and noticed problems after running gdb.base/huge.exp: gdb
    not being able to spawn for a large number of test-cases afterwards.

    So I investigated the memory usage, on my usual x86_64-linux development
    platform.

    The test-case is compiled with -DCRASH_GDB=2097152, so this:
    ...
    static int a[CRASH_GDB], b[CRASH_GDB];
    ...
    with sizeof (int) == 4 represents two arrays of 8MB each.

    Say we add a loop around the "print a" command and print space usage
    statistics:
    ...
    gdb_test "maint set per-command space on"
    for {set i 0} {$i < 100} {incr i} {
        gdb_test "print a"
    }
    ...

    This gets us:
    ...
    (gdb) print a^M
    $1 = {0 <repeats 2097152 times>}^M
    Space used: 478248960 (+469356544 for this command)^M
    (gdb) print a^M
    $2 = {0 <repeats 2097152 times>}^M
    Space used: 486629376 (+8380416 for this command)^M
    (gdb) print a^M
    $3 = {0 <repeats 2097152 times>}^M
    Space used: 495009792 (+8380416 for this command)^M
      ...
    (gdb) print a^M
    $100 = {0 <repeats 2097152 times>}^M
    Space used: 1308721152 (+8380416 for this command)^M
    ...

    In other words, we start out at 8MB, and the first print costs us about
469MB,
    and subsequent prints 8MB, which accumulates to 1.3 GB usage. [ On the
    i686-linux laptop, the first print costs us 335MB. ]

    The subsequent 8MBs are consistent with the values being saved into the
value
    history, but the usage for the initial print seems somewhat excessive.

    There is a PR open about needing sparse representation of large arrays
    (PR8819), but this memory usage points to an independent problem.

    The function value_print_array_elements contains a scoped_value_mark to
free
    allocated values in the outer loop, but it doesn't prevent the inner loop
from
    allocating a lot of values.

    Fix this by adding a scoped_value_mark in the inner loop, after which we
have:
    ...
    (gdb) print a^M
    $1 = {0 <repeats 2097152 times>}^M
    Space used: 8892416 (+0 for this command)^M
    (gdb) print a^M
    $2 = {0 <repeats 2097152 times>}^M
    Space used: 8892416 (+0 for this command)^M
    (gdb) print a^M
    $3 = {0 <repeats 2097152 times>}^M
    Space used: 8892416 (+0 for this command)^M
      ...
    (gdb) print a^M
    $100 = {0 <repeats 2097152 times>}^M
    Space used: 8892416 (+0 for this command)^M
    ...

    Note that the +0 here just means that the mallocs did not trigger an sbrk.
    This is dependent on malloc (which can use either mmap or sbrk or some
    pre-allocated memory) and will likely vary between different tunings,
versions
    and implementations, so this does not give us a reliable way detect the
    problem in a minimal way.

    A more reliable way of detecting the problem is:
    ...
     void
     value_free_to_mark (const struct value *mark)
     {
    +  size_t before = all_values.size ();
       auto iter = std::find (all_values.begin (), all_values.end (), mark);
       if (iter == all_values.end ())
         all_values.clear ();
       else
         all_values.erase (iter + 1, all_values.end ());
    +  size_t after = all_values.size ();
    +  if (before - after >= 1024)
    +    fprintf (stderr, "value_free_to_mark freed %zu items\n", before -
after);
    ...
    which without the fix tells us:
    ...
    +print a
    value_free_to_mark freed 2097152 items
    $1 = {0 <repeats 2097152 times>}
    ...

    Fix a similar problem for Fortran:
    ...
    +print array1
    value_free_to_mark freed 4194303 items
    $1 = (0, <repeats 2097152 times>)
    ...
    in fortran_array_printer_impl::process_element.

    The problem also exists for Ada:
    ...
    +print Arr
    value_free_to_mark freed 2097152 items
    $1 = (0 <repeats 2097152 times>)
    ...
    but is fixed by the fix for C.

    Add Fortran and Ada variants of the test-case.  The *.exp files are similar
    enough to the original to keep the copyright years range.

    While writing the Fortran test-case, I ran into needing an additional print
    setting to print the entire array in repeat form, filed as PR exp/30817.

    I managed to apply the compilation loop for the Ada variant as well, but
with
    a cumbersome repetition style.  I noticed no other test-case uses gnateD,
so
    perhaps there's a better way of implementing this.

    The regression test included in the patch is formulated in its weakest
    form, to avoid false positive FAILs, which also means that smaller
regressions
    may not get detected.

    Tested on x86_64-linux.

    Approved-By: Tom Tromey <tom@tromey.com>

-- 
You are receiving this mail because:
You are on the CC list for the bug.

^ permalink raw reply	[flat|nested] 2+ messages in thread

end of thread, other threads:[~2023-09-14 18:34 UTC | newest]

Thread overview: 2+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2023-09-01 11:22 [Bug exp/30817] New: [gdb/exp] Different interpretation of print options between C and Fortran vries at gcc dot gnu.org
2023-09-14 18:34 ` [Bug exp/30817] " cvs-commit at gcc dot gnu.org

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for read-only IMAP folder(s) and NNTP newsgroup(s).