On Mon, Dec 2, 2024 at 1:50 AM Lewis Hyatt <lhy...@gmail.com> wrote: > > With the codebase having already been prepared to handle it, change > location_t to be a 64-bit integer instead of a 32-bit integer.
OK if there's no comments from others within 48h. Thanks, Richard. > libcpp/ChangeLog: > > * include/cpplib.h (struct cpp_token): Adjust comment about the > struct size. > * include/line-map.h (location_t): Change typedef from 32-bit to > 64-bit > integer. > (LINE_MAP_MAX_COLUMN_NUMBER): Increase size to be appropriate for > 64-bit location_t. > (LINE_MAP_MAX_LOCATION_WITH_PACKED_RANGES): Likewise. > (LINE_MAP_MAX_LOCATION_WITH_COLS): Likewise. > (LINE_MAP_MAX_LOCATION): Likewise. > (MAX_LOCATION_T): Likewise. > (line_map_suggested_range_bits): Likewise. > (struct line_map): Adjust comment about the struct size. > (struct line_map_macro): Likewise. > (struct line_map_ordinary): Likewise. Rearrange fields to optimize > padding. > > gcc/testsuite/ChangeLog: > > * g++.dg/diagnostic/pr77949.C: Adapt the test for 64-bit location_t, > when the previously expected failure doesn't actually happen. > * g++.dg/modules/loc-prune-4.C: Adjust the expected output for the > 64-bit location_t case. > * gcc.dg/plugin/expensive_selftests_plugin.c: Don't try to test > the maximum supported column number in 64-bit location_t mode. > * gcc.dg/plugin/location_overflow_plugin.c: Adjust the base_location > so it can effectively test 64-bit location_t. > --- > libcpp/include/cpplib.h | 6 ++- > libcpp/include/line-map.h | 48 +++++++++++-------- > gcc/testsuite/g++.dg/diagnostic/pr77949.C | 5 +- > gcc/testsuite/g++.dg/modules/loc-prune-4.C | 6 +-- > .../plugin/expensive_selftests_plugin.cc | 10 ++-- > .../gcc.dg/plugin/location_overflow_plugin.cc | 5 ++ > 6 files changed, 48 insertions(+), 32 deletions(-) > > diff --git a/libcpp/include/cpplib.h b/libcpp/include/cpplib.h > index e73f77e67d8..73dd97df747 100644 > --- a/libcpp/include/cpplib.h > +++ b/libcpp/include/cpplib.h > @@ -255,8 +255,10 @@ struct GTY(()) cpp_identifier { > spelling; > }; > > -/* A preprocessing token. This has been carefully packed and should > - occupy 16 bytes on 32-bit hosts and 24 bytes on 64-bit hosts. */ > +/* A preprocessing token. This occupies 32 bytes on a 64-bit host. On a > + 32-bit host it occupies 20 or 24 bytes, depending whether a uint64_t > + requires 4- or 8-byte alignment. */ > + > struct GTY(()) cpp_token { > > /* Location of first char of token, together with range of full token. */ > diff --git a/libcpp/include/line-map.h b/libcpp/include/line-map.h > index 96fdf60644f..19fd64b9363 100644 > --- a/libcpp/include/line-map.h > +++ b/libcpp/include/line-map.h > @@ -291,7 +291,10 @@ enum lc_reason > > To further see how location_t works in practice, see the > worked example in libcpp/location-example.txt. */ > -typedef unsigned int location_t; > + > +/* A 64-bit type to represent a location. We only use 63 of the 64 bits, so > + that two location_t can be safely subtracted and stored in an int64_t. */ > +typedef uint64_t location_t; > typedef int64_t location_diff_t; > > /* Sometimes we need a type that has the same size as location_t but that > does > @@ -302,24 +305,31 @@ typedef location_t line_map_uint_t; > /* Do not track column numbers higher than this one. As a result, the > range of column_bits is [12, 18] (or 0 if column numbers are > disabled). */ > -const unsigned int LINE_MAP_MAX_COLUMN_NUMBER = (1U << 12); > +const unsigned int LINE_MAP_MAX_COLUMN_NUMBER = (1U << 31) - 1; > > /* Do not pack ranges if locations get higher than this. > If you change this, update: > gcc.dg/plugin/location-overflow-test-*.c. */ > -const location_t LINE_MAP_MAX_LOCATION_WITH_PACKED_RANGES = 0x50000000; > +const location_t LINE_MAP_MAX_LOCATION_WITH_PACKED_RANGES > + = location_t (0x50000000) << 31; > > /* Do not track column numbers if locations get higher than this. > If you change this, update: > gcc.dg/plugin/location-overflow-test-*.c. */ > -const location_t LINE_MAP_MAX_LOCATION_WITH_COLS = 0x60000000; > +const location_t LINE_MAP_MAX_LOCATION_WITH_COLS > + = location_t (0x60000000) << 31; > + > +/* Highest possible source location encoded within an ordinary map. Higher > + values up to MAX_LOCATION_T represent macro virtual locations. */ > +const location_t LINE_MAP_MAX_LOCATION = location_t (0x70000000) << 31; > > -/* Highest possible source location encoded within an ordinary map. */ > -const location_t LINE_MAP_MAX_LOCATION = 0x70000000; > +/* This is the highest possible source location encoded within an > + ordinary or macro map. */ > +const location_t MAX_LOCATION_T = location_t (-1) >> 2; > > /* This is the number of range bits suggested to enable, if range tracking is > desired. */ > -const int line_map_suggested_range_bits = 5; > +const int line_map_suggested_range_bits = 7; > > /* A range of source locations. > > @@ -397,7 +407,7 @@ typedef size_t (*line_map_round_alloc_size_func) (size_t); > struct GTY((tag ("0"), desc ("MAP_ORDINARY_P (&%h) ? 1 : 2"))) line_map { > location_t start_location; > > - /* Size and alignment is (usually) 4 bytes. */ > + /* Size is 8 bytes; alignment 4 or 8 depending on the arch. */ > }; > > /* An ordinary line map encodes physical source locations. Those > @@ -413,7 +423,7 @@ struct GTY((tag ("0"), desc ("MAP_ORDINARY_P (&%h) ? 1 : > 2"))) line_map { > > The highest possible source location is MAX_LOCATION_T. */ > struct GTY((tag ("1"))) line_map_ordinary : public line_map { > - /* Base class is 4 bytes. */ > + /* Base class is 8 bytes. */ > > /* 4 bytes of integers, each 1 byte for easy extraction/insertion. */ > > @@ -445,9 +455,7 @@ struct GTY((tag ("1"))) line_map_ordinary : public > line_map { > +-------------------------+-----------------------+-------------------+ > */ > unsigned int m_range_bits : 8; > > - /* Pointer alignment boundary on both 32 and 64-bit systems. */ > - > - const char *to_file; > + /* 32-bit int even in 64-bit mode. */ > linenum_type to_line; > > /* Location from whence this line map was included. For regular > @@ -456,12 +464,11 @@ struct GTY((tag ("1"))) line_map_ordinary : public > line_map { > within a map. */ > location_t included_from; > > - /* Size is 20 or 24 bytes, no padding */ > -}; > + /* Pointer alignment boundary, whether 32-bit or 64-bit mode. */ > + const char *to_file; > > -/* This is the highest possible source location encoded within an > - ordinary or macro map. */ > -const location_t MAX_LOCATION_T = 0x7FFFFFFF; > + /* Size is 28 (32) bytes for 32-bit (64-bit) arch. */ > +}; > > struct cpp_hashnode; > > @@ -480,7 +487,7 @@ struct GTY((tag ("2"))) line_map_macro : public line_map { > return m_expansion; > } > > - /* Base is 4 bytes. */ > + /* Base is 8 bytes. */ > > /* The number of tokens inside the replacement-list of MACRO. */ > unsigned int n_tokens; > @@ -556,7 +563,10 @@ struct GTY((tag ("2"))) line_map_macro : public line_map > { > if we are in a nested expansion context not. */ > location_t m_expansion; > > - /* Size is 20 or 32 (4 bytes padding on 64-bit). */ > + /* Size is one of the following: > + 32-bit system: 28 or 32 bytes, depending whether a uint64_t requires > + 4- or 8-byte alignment. > + 64-bit arch: 40 bytes. */ > }; > > #if CHECKING_P && (GCC_VERSION >= 2007) > diff --git a/gcc/testsuite/g++.dg/diagnostic/pr77949.C > b/gcc/testsuite/g++.dg/diagnostic/pr77949.C > index b81d6e2bb46..e1a201e52c0 100644 > --- a/gcc/testsuite/g++.dg/diagnostic/pr77949.C > +++ b/gcc/testsuite/g++.dg/diagnostic/pr77949.C > @@ -1,7 +1,10 @@ > -// Ensure that no fix-it hints are emitted > +// Ensure that fix-it hints are emitted even at a large column number. > // { dg-options "-fdiagnostics-parseable-fixits" } > > /* Very long line, where a missing semicolon would be suggested for > insertion at column 4097. */ > class test { > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > > } > // { dg-error "-: expected .;. after class definition" "" { target *-*-* } > .-1 } > +/* { dg-begin-multiline-output "" } > +fix-it: > +{ dg-end-multiline-output "" } */ > diff --git a/gcc/testsuite/g++.dg/modules/loc-prune-4.C > b/gcc/testsuite/g++.dg/modules/loc-prune-4.C > index aa8f248b52b..19e85d8d8a6 100644 > --- a/gcc/testsuite/g++.dg/modules/loc-prune-4.C > +++ b/gcc/testsuite/g++.dg/modules/loc-prune-4.C > @@ -16,7 +16,7 @@ int bar (int); // merge lines > int baz (int); > > > -// { dg-final { scan-lang-dump {Ordinary maps:2 locs:12288 range_bits:5} > module } } > +// { dg-final { scan-lang-dump {Ordinary maps:2 locs:49152 range_bits:7} > module } } > // { dg-final { scan-lang-dump { 1 source file names\n Source > file...=[^\n]*loc-prune-4.C\n} module } } > -// { dg-final { scan-lang-dump { Span:0 ordinary > \[[0-9]+\+12288,\+4096\)->\[0,\+4096\)} module } } > -// { dg-final { scan-lang-dump { Span:1 ordinary > \[[0-9]+\+40960,\+8192\)->\[4096,\+8192\)} module } } > +// { dg-final { scan-lang-dump { Span:0 ordinary > \[[0-9]+\+49152,\+16384\)->\[0,\+16384\)} module } } > +// { dg-final { scan-lang-dump { Span:1 ordinary > \[[0-9]+\+163840,\+32768\)->\[16384,\+32768\)} module } } > diff --git a/gcc/testsuite/gcc.dg/plugin/expensive_selftests_plugin.cc > b/gcc/testsuite/gcc.dg/plugin/expensive_selftests_plugin.cc > index e96efe0bed5..217e8f8c9cb 100644 > --- a/gcc/testsuite/gcc.dg/plugin/expensive_selftests_plugin.cc > +++ b/gcc/testsuite/gcc.dg/plugin/expensive_selftests_plugin.cc > @@ -63,17 +63,13 @@ test_richloc (rich_location *richloc) > static void > test_fixit_on_very_long_line (const line_table_case &case_) > { > - /* Various interesting column/line-width values, to try to tickle > - out bugs. */ > + /* Various interesting column/line-width values, to try to tickle out > bugs. In > + 64-bit location mode, we can't test the max because the maximum > supported > + column is unreasonably large. */ > const int VERY_LONG_LINE = 8192; > const int columns[] = {0, > 1, > 80, > - LINE_MAP_MAX_COLUMN_NUMBER - 2, > - LINE_MAP_MAX_COLUMN_NUMBER - 1, > - LINE_MAP_MAX_COLUMN_NUMBER, > - LINE_MAP_MAX_COLUMN_NUMBER + 1, > - LINE_MAP_MAX_COLUMN_NUMBER + 2, > VERY_LONG_LINE, > VERY_LONG_LINE + 5}; > for (unsigned int width_idx = 0; width_idx < ARRAY_SIZE (columns); > diff --git a/gcc/testsuite/gcc.dg/plugin/location_overflow_plugin.cc > b/gcc/testsuite/gcc.dg/plugin/location_overflow_plugin.cc > index 45a01b5f917..f731b1421b0 100644 > --- a/gcc/testsuite/gcc.dg/plugin/location_overflow_plugin.cc > +++ b/gcc/testsuite/gcc.dg/plugin/location_overflow_plugin.cc > @@ -84,6 +84,11 @@ plugin_init (struct plugin_name_args *plugin_info, > if (!base_location) > error_at (UNKNOWN_LOCATION, "missing plugin argument"); > > + /* With 64-bit locations, the thresholds are larger, so shift the base > + location argument accordingly. */ > + gcc_assert (sizeof (location_t) == sizeof (uint64_t)); > + base_location = 1 + ((base_location - 1) << 31); > + > register_callback (plugin_info->base_name, > PLUGIN_PRAGMAS, > on_pragma_registration,