This is an archive of the discontinued LLVM Phabricator instance.

[Parse] Improve diagnostic and recoveryy when there is an extra override in the outline method definition.
ClosedPublic

Authored by hokein on Oct 15 2021, 5:48 AM.

Details

Summary

The clang behavior was poor before this patch:

void B::foo() override {}
// Before: clang emited "expcted function body after function
// declarator", and skiped all contents until it hits a ";", the
// following function f() is discarded.

// VS

// Nnow "override is not allowed" with a remove fixit, and following f()
// is retained.
void f();

Diff Detail

Event Timeline

hokein requested review of this revision.Oct 15 2021, 5:48 AM
hokein created this revision.
Herald added a project: Restricted Project. · View Herald TranscriptOct 15 2021, 5:48 AM
sammccall accepted this revision.Oct 15 2021, 1:15 PM

This seems very nice to me, I'd hit the bad diagnostic before but hadn't noticed the bad recovery.
AFAICT this can't break any valid code.

clang/include/clang/Basic/DiagnosticParseKinds.td
962

virt-specifier is standardese. I think dropping virt, i.e. 'override' specifier... is clear enough.

962

Hm, is "outside a class definition" the clearest way to explain the mistake?

I guess this is handling two classes of problem:

  • repeating override on an out-of-line definition (motivating case)
  • placing override on a free function

I'd slightly prefer the motivating case to mention "out-of-line", but that wording doesn't fit the other case. I'm not sure whether it's worth trying to split them

clang/lib/Parse/ParseDecl.cpp
2039

Do we too have to consider K&R?

typedef int override;
void foo(a) 
    override a; 
{
}

I guess not because this behavior only fires for c++?

This revision is now accepted and ready to land.Oct 15 2021, 1:15 PM
hokein updated this revision to Diff 380291.Oct 18 2021, 12:49 AM
hokein marked 2 inline comments as done.

virt-specifier => specifier

clang/include/clang/Basic/DiagnosticParseKinds.td
962

yeah, the first one is the motivating case, I think it is the most common one, but I'm tempted to keep it as-is rather than creating a separate diagnostic message for a less-common case.

clang/lib/Parse/ParseDecl.cpp
2039

right, the change only affects C++ code -- isCXX11VirtSpecifier returns null for non-C++11-or-later code.

This revision was landed with ongoing or failed builds.Oct 18 2021, 1:00 AM
This revision was automatically updated to reflect the committed changes.