I tried a couple experiments with __int128 and found some gdb issues. My test code: __int128 x = 72; I compiled with -g -c then ran gdb on the .o. Printing kind of works, but chooses hex by default and zero-pads: (gdb) p x $1 = 0x00000000000000000000000000000048 Specifying decimal still zero-pads, which looks very weird: (gdb) p/d x $2 = 00000000000000000000000000000072 Addition doesn't work: (gdb) p x + 5 That operation is not available on integers of more than 8 bytes.
One super intrusive option would be to use GMP everywhere. Another possibility would be to redefine LONGEST as __int128 where available.
Handling the printing in bug 16225, so maybe this bug could be for the operations. See some discussion in bug 21185 for how to do that.
Another issue is that c-exp.y has productions for things like "unsigned long" and "long unsigned" -- but there isn't one for __int128. This came up during the alignment patch.
(In reply to Tom Tromey from comment #0) > I tried a couple experiments with __int128 and found some gdb issues. > > My test code: > > __int128 x = 72; > > I compiled with -g -c then ran gdb on the .o. > > Printing kind of works, but chooses hex by default and zero-pads: > > (gdb) p x > $1 = 0x00000000000000000000000000000048 > > Specifying decimal still zero-pads, which looks very weird: > > (gdb) p/d x > $2 = 00000000000000000000000000000072 > > Addition doesn't work: > > (gdb) p x + 5 > That operation is not available on integers of more than 8 bytes. There is no longer zero-padding since 8.1, but addition still doesn't work.
The master branch has been updated by Tom de Vries <vries@sourceware.org>: https://sourceware.org/git/gitweb.cgi?p=binutils-gdb.git;h=0057a7ee0d963eb9aee5cdfb9d6da5279bc8caf9 commit 0057a7ee0d963eb9aee5cdfb9d6da5279bc8caf9 Author: Tom de Vries <tdevries@suse.de> Date: Wed Jul 21 14:19:51 2021 +0200 [gdb/testsuite] Add KFAILs for gdb.ada FAILs with gcc-11 With gcc-11 we run into: ... (gdb) print pa_ptr.all^M That operation is not available on integers of more than 8 bytes.^M (gdb) KFAIL: gdb.ada/arrayptr.exp: scenario=all: print pa_ptr.all (PRMS: gdb/20991) ... This is due to PR exp/20991 - "__int128 type support". Mark this and similar FAILs as KFAIL. Also mark this FAIL: .... (gdb) print pa_ptr(3)^M cannot subscript or call something of type `foo__packed_array_ptr'^M (gdb) FAIL: gdb.ada/arrayptr.exp: scenario=minimal: print pa_ptr(3) ... as a KFAIL for PR ada/28115 - "Support packed array encoded as DW_TAG_subrange_type". Tested on x86_64-linux, with gcc-10 and gcc-11. gdb/testsuite/ChangeLog: 2021-07-21 Tom de Vries <tdevries@suse.de> * gdb.ada/arrayptr.exp: Add KFAILs for PR20991 and PR28115. * gdb.ada/exprs.exp: Add KFAILs for PR20991. * gdb.ada/packed_array_assign.exp: Same.
The gdb-11-branch branch has been updated by Tom de Vries <vries@sourceware.org>: https://sourceware.org/git/gitweb.cgi?p=binutils-gdb.git;h=f26101b199482bd13b5f9c45fb4f43a4eb8b16e6 commit f26101b199482bd13b5f9c45fb4f43a4eb8b16e6 Author: Tom de Vries <tdevries@suse.de> Date: Wed Jul 21 14:22:16 2021 +0200 [gdb/testsuite] Add KFAILs for gdb.ada FAILs with gcc-11 With gcc-11 we run into: ... (gdb) print pa_ptr.all^M That operation is not available on integers of more than 8 bytes.^M (gdb) KFAIL: gdb.ada/arrayptr.exp: scenario=all: print pa_ptr.all (PRMS: gdb/20991) ... This is due to PR exp/20991 - "__int128 type support". Mark this and similar FAILs as KFAIL. Also mark this FAIL: .... (gdb) print pa_ptr(3)^M cannot subscript or call something of type `foo__packed_array_ptr'^M (gdb) FAIL: gdb.ada/arrayptr.exp: scenario=minimal: print pa_ptr(3) ... as a KFAIL for PR ada/28115 - "Support packed array encoded as DW_TAG_subrange_type". Tested on x86_64-linux, with gcc-10 and gcc-11. gdb/testsuite/ChangeLog: 2021-07-21 Tom de Vries <tdevries@suse.de> * gdb.ada/arrayptr.exp: Add KFAILs for PR20991 and PR28115. * gdb.ada/exprs.exp: Add KFAILs for PR20991. * gdb.ada/packed_array_assign.exp: Same.
*** Bug 21185 has been marked as a duplicate of this bug. ***
In bug #21185, using gcc's wide-int was suggested as one option. I looked into this, and I can make wide-int compile in gdb with some hacks. However, since gdb already requires GMP, I think it's probably better to just use that. Also it seems like there are multiple parts to this bug. Perhaps we should treat them individually... * Parsers should recognize 128-bit types and lexers should make 128-bit quantities. * valops should extract a GMP from a struct value and work on that representation. * Type ranges / dynamic props should be converted to 128-bit quantities where needed. (My thinking here is that the data would be stored in some convenient & compact format, but convert to GMP when working with the values.)
GMP has a surprising and unfortunate design choice that IMHO may make it undesirable for a fixed-width type -- it uses the heap for _every_ integer. This is last discussed in this thread: https://sourceware.org/pipermail/gdb/2022-October/050375.html
(In reply to Pedro Alves from comment #9) > GMP has a surprising and unfortunate design choice that IMHO may make it > undesirable for a fixed-width type -- it uses the heap for _every_ integer. I suspect it won't matter much, but if it does, we can always adopt wide-int.
Yeah, or something else. As long as the type we use looks like an integer (implements arithmetic operators, etc.), then swapping one implementation for another is not a big deal.
I was looking at whether GMP already has built-in support for _finite_ precision, for example so that we handle wraparound of "unsigned __int128" values propertly, left shifting, etc. I couldn't find anything for that, so I guess we'd have to implement wraparound, etc. ourselves?
(In reply to Pedro Alves from comment #12) > I was looking at whether GMP already has built-in support for _finite_ > precision, for example so that we handle wraparound of "unsigned __int128" > values propertly, left shifting, etc. I couldn't find anything for that, so > I guess we'd have to implement wraparound, etc. ourselves? Yeah. I suppose gcc's is nicer this way, you can specify the precision.
> Yeah. I suppose gcc's is nicer this way, you can specify the > precision. It occurs to me, though, that not many things in gdb are using "chained" expressions. Normally we'd unpack a value to a GMP, operate on it, then put it back into a value. So, frequently, we wouldn't actually have to worry about the size of intermediates
That may be true. If we can make valarith.c:scalar_binop work for any kind of fixed-precision type instead of doing host arithmetic on LONGEST, with the precision being a runtime property, then we would get most of value arithmetic done for all types, including types wider than 128 bits when they come. It still seems to me though like if we need to implement the fixed-precision logic, we might as well consider factoring it out to an integer class. That type may be based on wide-int, some other integer template (there are plenty such templates around we could borrow), or a wrapper around GMP (or a fixed-precision wrapper around our C++ GMP infinite-precision wrapper).
Yeah. I even considered just writing our own. Monday or so I'll push my WIP patch to add wide-int to the tree and you can see what it looks like. A few hacks were needed, though nothing too serious. Mostly I couldn't be bothered to figure out how all the classes work. The main attraction of GMP is we already have it, and I recently added a few operators and such. For constants and values in type properties we can either just store the number on some obstack, or use LEB. The latter can be nice since we can sometimes just use a pointer directly into the DWARF data.
(In reply to Tom Tromey from comment #16) > Monday or so I'll push my WIP patch to add wide-int to the tree > and you can see what it looks like It is submit/wide-int-hacks in my github
See also submit/pr-20991-more-gmp for the WIP.
(In reply to Tom Tromey from comment #8) > Also it seems like there are multiple parts to this bug. > Perhaps we should treat them individually... I filed new bugs and I'm turning this into a meta bug.