[PATCH v2] implement -Winfinite-recursion [PR88232]
Jeff Law
jeffreyalaw@gmail.com
Tue Nov 23 19:11:10 GMT 2021
On 11/11/2021 2:46 PM, Martin Sebor via Gcc-patches wrote:
> Attached is a v2 of the solution I posted earlier this week
> with a few tweaks made after a more careful consideration of
> the problem and possible false negatives and positives.
>
> 1) It avoids warning for [apparently infinitely recursive] calls
> in noreturn functions where the recursion may be prevented by
> a call to a noreturn function.
> 2) It avoids warning for calls where the recursion may be prevented
> by a call to a longjmp or siglongjmp.
> 3) It warns for recursive calls to built-ins in definitions of
> the corresponding library functions (e.g., for a call to
> __builtin_malloc in malloc).
> 4) It warns for calls to C++ functions even if they call other
> functions that might throw and so break out of the infinite
> recursion. (E.g., operator new.) This is the same as Clang.
> 5) It doesn't warn for calls to C++ functions with the throw
> expression.
>
> Besides these changes to the warning itself, I've also improved
> the code a bit by making the workhorse function a member of
> the pass so recursive calls don't need to pass as many arguments
> to itself.
>
> Retested on x86_64-linux and by building Glibc and Binutils/GDB.
>
> A possible enhancement is to warn for calls to calloc, malloc,
> or realloc from within the definition of one of the other two
> functions. That might be a mistake made in code that tries
> naively to replace the allocator with its own implementation.
>
> On 11/9/21 9:28 PM, Martin Sebor wrote:
>> The attached patch adds support to the middle end for detecting
>> infinitely recursive calls. The warning is controlled by the new
>> -Winfinite-recursion option. The option name is the same as
>> Clang's.
>>
>> I scheduled the warning pass to run after early inlining to
>> detect mutually recursive calls but before tail recursion which
>> turns some recursive calls into infinite loops and so makes
>> the two indistinguishable.
>>
>> The warning detects a superset of problems detected by Clang
>> (based on its tests). It detects the problem in PR88232
>> (the feature request) as well as the one in PR 87742,
>> an unrelated problem report that was root-caused to bug due
>> to infinite recursion.
>>
>> This initial version doesn't attempt to deal with superimposed
>> symbols, so those might trigger false positives. I'm not sure
>> that's something to worry about.
>>
>> The tests are very light, but those for the exceptional cases
>> are exceedingly superficial, so it's possible those might harbor
>> some false positives and negatives.
>>
>> Tested on x86_64-linux.
>>
>> Martin
>>
>
>
> gcc-88232.diff
>
> Implement -Winfinite-recursion [PR88232].
>
> Resolves:
> PR middle-end/88232 - Please implement -Winfinite-recursion
>
> gcc/ChangeLog:
>
> PR middle-end/88232
> * Makefile.in (OBJS): Add gimple-warn-recursion.o.
> * common.opt: Add -Winfinite-recursion.
> * doc/invoke.texi (-Winfinite-recursion): Document.
> * passes.def (pass_warn_recursion): Schedule a new pass.
> * tree-pass.h (make_pass_warn_recursion): Declare.
> * gimple-warn-recursion.c: New file.
>
> gcc/c-family/ChangeLog:
>
> PR middle-end/88232
> * c.opt: Add -Winfinite-recursion.
>
> gcc/testsuite/ChangeLog:
>
> PR middle-end/88232
> * c-c++-common/attr-used-5.c: Suppress valid warning.
> * c-c++-common/attr-used-6.c: Same.
> * c-c++-common/attr-used-9.c: Same.
> * g++.dg/warn/Winfinite-recursion-2.C: New test.
> * g++.dg/warn/Winfinite-recursion-3.C: New test.
> * g++.dg/warn/Winfinite-recursion.C: New test.
> * gcc.dg/Winfinite-recursion-2.c: New test.
> * gcc.dg/Winfinite-recursion.c: New test.
This is OK. While there may be other improvements that could be made,
this looks like a reasonable warning as-is and can be extended/refined
as needed.
jeff
More information about the Gcc-patches
mailing list