gcc/c-family/ChangeLog:
PR c++/68819
* c-indentation.c (get_visual_column): Add location_t param.
Handle the column number being zero by effectively disabling the
warning, with an "inform".
(should_warn_for_misleading_indentation): Add location_t argument
for all uses of get_visual_column.
gcc/testsuite/ChangeLog:
PR c++/68819
PR preprocessor/69177
* gcc.dg/plugin/location-overflow-test-1.c: New test case.
* gcc.dg/plugin/location-overflow-test-2.c: New test case.
* gcc.dg/plugin/location_overflow_plugin.c: New test plugin.
* gcc.dg/plugin/plugin.exp (plugin_test_list): Add the above.
libcpp/ChangeLog:
PR preprocessor/69177
* line-map.c (LINE_MAP_MAX_LOCATION_WITH_PACKED_RANGES): New
constant.
(LINE_MAP_MAX_LOCATION_WITH_COLS): Add note about unit tests
to comment.
(can_be_stored_compactly_p): Reduce threshold from
LINE_MAP_MAX_LOCATION_WITH_COLS to
LINE_MAP_MAX_LOCATION_WITH_PACKED_RANGES.
(get_combined_adhoc_loc): Likewise.
(get_range_from_loc): Likewise.
(linemap_line_start): Ensure that a new ordinary map is created
when transitioning from range-packing being enabled to disabled,
at the LINE_MAP_MAX_LOCATION_WITH_PACKED_RANGES threshold. Set
range_bits to 0 for new ordinary maps when beyond this limit.
Prevent the "increase the column bits of a freshly created map"
optimization if the range bits has reduced.
git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@232379
138bc75d-0d04-0410-961f-
82ee72b054a4
+2016-01-14 David Malcolm <dmalcolm@redhat.com>
+
+ PR c++/68819
+ * c-indentation.c (get_visual_column): Add location_t param.
+ Handle the column number being zero by effectively disabling the
+ warning, with an "inform".
+ (should_warn_for_misleading_indentation): Add location_t argument
+ for all uses of get_visual_column.
+
2016-01-10 Patrick Palka <ppalka@gcc.gnu.org>
PR c++/69029
on the line. */
static bool
-get_visual_column (expanded_location exploc,
+get_visual_column (expanded_location exploc, location_t loc,
unsigned int *out,
unsigned int *first_nws)
{
+ /* PR c++/68819: if the column number is zero, we presumably
+ had a location_t > LINE_MAP_MAX_LOCATION_WITH_COLS, and so
+ we have no column information.
+ Act as if no conversion was possible, triggering the
+ error-handling path in the caller. */
+ if (!exploc.column)
+ {
+ static bool issued_note = false;
+ if (!issued_note)
+ {
+ /* Notify the user the first time this happens. */
+ issued_note = true;
+ inform (loc,
+ "-Wmisleading-indentation is disabled from this point"
+ " onwards, since column-tracking was disabled due to"
+ " the size of the code/headers");
+ }
+ return false;
+ }
+
int line_len;
const char *line = location_get_source_line (exploc.file, exploc.line,
&line_len);
gcc_assert (guard_exploc.line == next_stmt_exploc.line);
unsigned int guard_vis_column;
unsigned int guard_line_first_nws;
- if (!get_visual_column (guard_exploc,
+ if (!get_visual_column (guard_exploc, guard_loc,
&guard_vis_column,
&guard_line_first_nws))
return false;
the case for input files containing #line directives, and these
are often for autogenerated sources (e.g. from .md files), where
it's not clear that it's meaningful to look at indentation. */
- if (!get_visual_column (next_stmt_exploc, &next_stmt_vis_column,
+ if (!get_visual_column (next_stmt_exploc, next_stmt_loc,
+ &next_stmt_vis_column,
&next_stmt_line_first_nws))
return false;
- if (!get_visual_column (body_exploc,
+ if (!get_visual_column (body_exploc, body_loc,
&body_vis_column,
&body_line_first_nws))
return false;
- if (!get_visual_column (guard_exploc,
+ if (!get_visual_column (guard_exploc, guard_loc,
&guard_vis_column,
&guard_line_first_nws))
return false;
+2016-01-14 David Malcolm <dmalcolm@redhat.com>
+
+ PR c++/68819
+ PR preprocessor/69177
+ * gcc.dg/plugin/location-overflow-test-1.c: New test case.
+ * gcc.dg/plugin/location-overflow-test-2.c: New test case.
+ * gcc.dg/plugin/location_overflow_plugin.c: New test plugin.
+ * gcc.dg/plugin/plugin.exp (plugin_test_list): Add the above.
+
2016-01-14 Marek Polacek <polacek@redhat.com>
PR c/69262
--- /dev/null
+/* { dg-options "-Wmisleading-indentation -Wall -fplugin-arg-location_overflow_plugin-value=0x60000001" } */
+
+/* We use location_overflow_plugin.c, which injects the case that location_t
+ values have exceeded LINE_MAP_MAX_LOCATION_WITH_COLS, and hence no column
+ numbers are available. */
+
+/* Verify that we're in column-less mode. */
+extern unknown_type test; /* { dg-error "0: unknown type name" } */
+
+/* PR c++/68819: verify that -Wmisleading-indentation is suppressed. */
+
+int
+fn_1 (int flag)
+{
+ int x = 4, y = 5;
+ if (flag) x = 3; y = 2; /* { dg-message "disabled from this point" } */
+ return x * y;
+}
+
+/* ...and that a "sorry" is only emitted the first time. */
+
+int
+fn_2 (int flag)
+{
+ int x = 4, y = 5;
+ if (flag) x = 3; y = 2; /* { dg-bogus "sorry" } */
+ return x * y;
+}
--- /dev/null
+/* { dg-options "-fdiagnostics-show-caret -Wmisleading-indentation -Wall -fplugin-arg-location_overflow_plugin-value=0x50000001" } */
+
+/* We use location_overflow_plugin.c, which injects the case that location_t
+ values have exceeded LINE_MAP_MAX_LOCATION_WITH_PACKED_RANGES, and hence
+ no range-packing should occur. */
+
+/* Verify that we still have column numbers. */
+extern unknown_type test; /* { dg-error "8: unknown type name" } */
+
+/* ...and ranges. */
+/* { dg-begin-multiline-output "" }
+ extern unknown_type test;
+ ^~~~~~~~~~~~
+ { dg-end-multiline-output "" } */
+
+
+/* PR c++/68819: verify that -Wmisleading-indentation is still available. */
+
+int
+fn_1 (int flag)
+{
+ int foo = 4, bar = 5;
+ if (flag) foo = 3; bar = 2; /* { dg-warning "indented" } */
+ return foo * bar;
+}
+
+/* Verify that we still have ranges, despite the lack of packing. */
+
+/* { dg-begin-multiline-output "" }
+ if (flag) foo = 3; bar = 2;
+ ^~~
+ { dg-end-multiline-output "" } */
+/* { dg-begin-multiline-output "" }
+ if (flag) foo = 3; bar = 2;
+ ^~
+ { dg-end-multiline-output "" } */
--- /dev/null
+/* Plugin for testing how gracefully we degrade in the face of very
+ large source files. */
+
+#include "config.h"
+#include "gcc-plugin.h"
+#include "system.h"
+#include "coretypes.h"
+#include "spellcheck.h"
+#include "diagnostic.h"
+
+int plugin_is_GPL_compatible;
+
+static location_t base_location;
+
+/* Callback handler for the PLUGIN_START_UNIT event; pretend
+ we parsed a very large include file. */
+
+static void
+on_start_unit (void */*gcc_data*/, void */*user_data*/)
+{
+ /* Act as if we've already parsed a large body of code;
+ so that we can simulate various fallbacks in libcpp:
+
+ 0x50000001 > LINE_MAP_MAX_LOCATION_WITH_PACKED_RANGES:
+ this will trigger the creation of line maps with range_bits == 0
+ so that all ranges will be stored in the ad-hoc lookaside.
+
+ 0x60000001 > LINE_MAP_MAX_LOCATION_WITH_COLS:
+ this will trigger the creation of line maps with column_bits == 0
+ and hence we will immediately degrade to having locations in which
+ column number is 0. */
+ line_table->highest_location = base_location;
+}
+
+/* We add some extra testing during diagnostics by chaining up
+ to the finalizer. */
+
+static diagnostic_finalizer_fn original_finalizer = NULL;
+
+static void
+verify_unpacked_ranges (diagnostic_context *context,
+ diagnostic_info *diagnostic)
+{
+ /* Verify that the locations are ad-hoc, not packed. */
+ location_t loc = diagnostic_location (diagnostic);
+ gcc_assert (IS_ADHOC_LOC (loc));
+
+ /* We're done testing; chain up to original finalizer. */
+ gcc_assert (original_finalizer);
+ original_finalizer (context, diagnostic);
+}
+
+static void
+verify_no_columns (diagnostic_context *context,
+ diagnostic_info *diagnostic)
+{
+ /* Verify that the locations have no columns. */
+ location_t loc = diagnostic_location (diagnostic);
+ gcc_assert (LOCATION_COLUMN (loc) == 0);
+
+ /* We're done testing; chain up to original finalizer. */
+ gcc_assert (original_finalizer);
+ original_finalizer (context, diagnostic);
+}
+
+int
+plugin_init (struct plugin_name_args *plugin_info,
+ struct plugin_gcc_version */*version*/)
+{
+ /* Read VALUE from -fplugin-arg-location_overflow_plugin-value=<VALUE>
+ in hexadecimal form into base_location. */
+ for (int i = 0; i < plugin_info->argc; i++)
+ {
+ if (0 == strcmp (plugin_info->argv[i].key, "value"))
+ base_location = strtol (plugin_info->argv[i].value, NULL, 16);
+ }
+
+ if (!base_location)
+ error_at (UNKNOWN_LOCATION, "missing plugin argument");
+
+ register_callback (plugin_info->base_name,
+ PLUGIN_START_UNIT,
+ on_start_unit,
+ NULL); /* void *user_data */
+
+ /* Hack in additional testing, based on the exact value supplied. */
+ original_finalizer = diagnostic_finalizer (global_dc);
+ switch (base_location)
+ {
+ case 0x50000001:
+ diagnostic_finalizer (global_dc) = verify_unpacked_ranges;
+ break;
+
+ case 0x60000001:
+ diagnostic_finalizer (global_dc) = verify_no_columns;
+ break;
+
+ default:
+ error_at (UNKNOWN_LOCATION, "unrecognized value for plugin argument");
+ }
+
+ return 0;
+}
{ diagnostic_plugin_show_trees.c \
diagnostic-test-show-trees-1.c } \
{ levenshtein_plugin.c levenshtein-test-1.c } \
+ { location_overflow_plugin.c \
+ location-overflow-test-1.c \
+ location-overflow-test-2.c } \
]
foreach plugin_test $plugin_test_list {
+2016-01-14 David Malcolm <dmalcolm@redhat.com>
+
+ PR preprocessor/69177
+ * line-map.c (LINE_MAP_MAX_LOCATION_WITH_PACKED_RANGES): New
+ constant.
+ (LINE_MAP_MAX_LOCATION_WITH_COLS): Add note about unit tests
+ to comment.
+ (can_be_stored_compactly_p): Reduce threshold from
+ LINE_MAP_MAX_LOCATION_WITH_COLS to
+ LINE_MAP_MAX_LOCATION_WITH_PACKED_RANGES.
+ (get_combined_adhoc_loc): Likewise.
+ (get_range_from_loc): Likewise.
+ (linemap_line_start): Ensure that a new ordinary map is created
+ when transitioning from range-packing being enabled to disabled,
+ at the LINE_MAP_MAX_LOCATION_WITH_PACKED_RANGES threshold. Set
+ range_bits to 0 for new ordinary maps when beyond this limit.
+ Prevent the "increase the column bits of a freshly created map"
+ optimization if the range bits has reduced.
+
2016-01-08 Jakub Jelinek <jakub@redhat.com>
PR c++/69145
disabled). */
const unsigned int LINE_MAP_MAX_COLUMN_NUMBER = (1U << 12);
-/* Do not track column numbers if locations get higher than this. */
+/* Do not pack ranges if locations get higher than this.
+ If you change this, update:
+ gcc.dg/plugin/location_overflow_plugin.c
+ gcc.dg/plugin/location-overflow-test-*.c. */
+const source_location LINE_MAP_MAX_LOCATION_WITH_PACKED_RANGES = 0x50000000;
+
+/* Do not track column numbers if locations get higher than this.
+ If you change this, update:
+ gcc.dg/plugin/location_overflow_plugin.c
+ gcc.dg/plugin/location-overflow-test-*.c. */
const source_location LINE_MAP_MAX_LOCATION_WITH_COLS = 0x60000000;
/* Highest possible source location encoded within an ordinary or
if (src_range.m_start < RESERVED_LOCATION_COUNT)
return false;
- if (locus >= LINE_MAP_MAX_LOCATION_WITH_COLS)
+ if (locus >= LINE_MAP_MAX_LOCATION_WITH_PACKED_RANGES)
return false;
/* All 3 locations must be within ordinary maps, typically, the same
/* Any ordinary locations ought to be "pure" at this point: no
compressed ranges. */
linemap_assert (locus < RESERVED_LOCATION_COUNT
- || locus >= LINE_MAP_MAX_LOCATION_WITH_COLS
+ || locus >= LINE_MAP_MAX_LOCATION_WITH_PACKED_RANGES
|| locus >= LINEMAPS_MACRO_LOWEST_LOCATION (set)
|| pure_location_p (set, locus));
/* For ordinary maps, extract packed range. */
if (loc >= RESERVED_LOCATION_COUNT
&& loc < LINEMAPS_MACRO_LOWEST_LOCATION (set)
- && loc <= LINE_MAP_MAX_LOCATION_WITH_COLS)
+ && loc <= LINE_MAP_MAX_LOCATION_WITH_PACKED_RANGES)
{
const line_map *map = linemap_lookup (set, loc);
const line_map_ordinary *ordmap = linemap_check_ordinary (map);
&& line_delta * map->m_column_and_range_bits > 1000)
|| (max_column_hint >= (1U << effective_column_bits))
|| (max_column_hint <= 80 && effective_column_bits >= 10)
+ || (highest > LINE_MAP_MAX_LOCATION_WITH_PACKED_RANGES
+ && map->m_range_bits > 0)
|| (highest > LINE_MAP_MAX_LOCATION_WITH_COLS
&& (set->max_column_hint || highest >= LINE_MAP_MAX_SOURCE_LOCATION)))
add_map = true;
else
{
column_bits = 7;
- range_bits = set->default_range_bits;
+ if (highest <= LINE_MAP_MAX_LOCATION_WITH_PACKED_RANGES)
+ range_bits = set->default_range_bits;
+ else
+ range_bits = 0;
while (max_column_hint >= (1U << column_bits))
column_bits++;
max_column_hint = 1U << column_bits;
single line we can sometimes just increase its column_bits instead. */
if (line_delta < 0
|| last_line != ORDINARY_MAP_STARTING_LINE_NUMBER (map)
- || SOURCE_COLUMN (map, highest) >= (1U << column_bits))
+ || SOURCE_COLUMN (map, highest) >= (1U << column_bits)
+ || range_bits < map->m_range_bits)
map = linemap_check_ordinary
(const_cast <line_map *>
(linemap_add (set, LC_RENAME,