mgehre / llvm-project

The home of the clang-based implementation of lifetime safety warnings.
39 stars 4 forks source link

Current status and future plans? #98

Open ispeters opened 3 years ago

ispeters commented 3 years ago

I'm looking into the feasibility of adding a job to our continuous integration that builds our source with -Wlifetime enabled. We rely on some pretty recent Clang fixes for coroutine bugs so I'm worried that simply building with your latest version will fail.

Do you have plans to merge from upstream's main branch again soon?

Would you be open to PRs that cherry-pick the upstream coroutine fixes?

Is there anything else you can tell me about the project's current state and near future?

cc @bcardosolopes

Xazax-hun commented 3 years ago

Hey, thanks for being interested!

Currently, we do not work on -Wlifetime actively. One of the main reasons is that contracts were not part of C++20 and we planned to piggy back on the contract implementation. (We did have a lightweight implementation for a small subset of contracts for the interim period.)

There are certain parts of -Wlifetime that are already part of upstream clang. Those are mainly the statement local parts of the analysis. There are some examples about the capabilities of those warnings here: https://github.com/llvm/llvm-project/blob/main/clang/test/Sema/warn-lifetime-analysis-nocfg.cpp

They found many errors in real world code and is on by default. Hopefully once contracts are on track again we can continue to improve/implement the rest of the analysis.

GunpowderGuy commented 2 years ago

@Xazax-hun Where can we get information about the current status of contracts?

duneroadrunner commented 3 months ago

Seeing as this project seems to have been in cold storage for some time without a successor, and pressure is seemingly mounting to abandon "unsafe" C++, I'm going to invite anyone still interested (in static enforcement of lifetime safety) to check out scpptool (my project).

It's a static analyzer designed to (along with an accompanying library) fully enforce a practical and high-performance memory and data race safe subset of C++. It differs from the "lifetime profile checker" approach (taken by this project), in a few ways:

First, the accompanying library is not only much more extensive than the GSL (the accompanying library for this project), in terms of providing options for run-time checked safety, it is even more extensive than the (clang) sanitizers. While resorting to run-time checks is not the preferred option, it means that almost all existing (unsafe) C++ elements can be directly mapped to (and therefore auto-converted to) counterparts in the safe subset. (Notably, this includes self/mutual/cyclic references irrespective of how and where the target objects are allocated.)

This means that, just as the sanitizers effectively "auto-convert" an intermediate representation of the code to an equivalent one with added run-time checks during the build, in theory, any (reasonable) C/C++ code could be auto-converted to the safe subset of C++ as a build step.

While run-time mechanisms are a good fallback option, ideally we would prefer that existing/legacy code either get replaced with zero-overhead safe code, or just be verified as safe in its original form. In this respect, the scpptool static analyzer is a little more limited than the one in this project in the sense that the scpptool analyzer does not use "flow sensitive" (or "path sensitive") analysis. The determination of whether an operation is safe or not is based only on the elements involved in the operation and their declarations, not any other preceding operations.

This limitation results in (modestly) more places where run-time checked elements will have to be used. But I've found that in practice, those extra run-time checked elements rarely occur inside performance sensitive inner loops. So at this point I feel fairly confident that the "scalability" and simplicity benefits of foregoing "flow sensitive" analysis outweigh the minor (if not negligible) potential performance costs. (And I guess the potential "unreliability" that comes with the possibility of any of the additional run-time checks failing.)

Again, while the set of code that can be verified as safe in its original form is a little smaller with scpptool, (reasonable) C/C++ can be auto-converted to the safe subset (in theory, as a build step if desired). So while getting an existing legacy codebase to conform to the scpptool analyzer's restrictions might require a few percent more modifications than would be required to conform to this project's static analyzer, the work required to make those modifications is potentially much less when scpptool's auto-conversion feature is used.

(Btw, don't mind the verbose syntax of the scpptool annotations and associated library. More concise aliases for the syntax are expected in the future.)

duneroadrunner commented 3 months ago

Btw, out of curiosity, what did this project need from the (elusive) C++ contracts feature? I'm not super familiar with the contracts proposal, but for example it doesn't seem to me that either the scpptool or the Rust analyzer needed contracts.