Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
11 changes: 0 additions & 11 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -445,17 +445,6 @@ void bar(std::vector<std::unique_ptr<int>>& cont, std::unique_ptr<int>& p)
}
```

You can use `-Wlifetime-container-move` to enable check for it. But it's always better to introduce a helper function to state your intent:

```cpp
// pset(container) = {*container}
move_each(std::move(container), [](auto&& elem){
// use elem
});
// pset(container) = {invalid}
assert(container.empty());
```

# Difference from the original implementation
## Output variable
### Return check
Expand Down
1 change: 0 additions & 1 deletion include/cppsafe/Options.h
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,6 @@ struct CppsafeOptions {
bool LifetimeDisabled = false;
bool LifetimeGlobal = false;
bool LifetimeOutput = false;
bool LifetimeContainerMove = false;
};

}
78 changes: 0 additions & 78 deletions integration_test/feature/move_container.cpp

This file was deleted.

22 changes: 17 additions & 5 deletions lib/lifetime/LifetimePsetBuilder.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -841,12 +841,24 @@ class PSetsBuilder final : public ConstStmtVisitor<PSetsBuilder, void>, public P
}

if (PS.containsParent(V)) {
// WORKAROUND: https://github.com/qqiangwu/cppsafe/issues/82
//
// when move var with pset {*container}, only invalidate the var itself,
// containers and iterators are not invalidated
if (!Reporter.getOptions().LifetimeContainerMove) {
if (V.isDeref() && isIteratorOrContainer(Var.getType())) {
continue;
}
// containers and iterators are not invalidated.
// <code>
// void foo(std::vector<std::unique_ptr<int>>& cont, std::unique_ptr<int>& p)
//{
// for (auto& x : cont) {
// p = std::move(x);
//}

// for (auto& x: cont) {
// use(x);
//}
//}
//</code>
if (V.isDeref() && isIteratorOrContainer(Var.getType())) {
continue;
}
setPSet(PSet::singleton(Var), PSet::invalid(Reason), Reason.getRange());
}
Expand Down
4 changes: 0 additions & 4 deletions src/main.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -62,9 +62,6 @@ static const cl::opt<bool> WarnLifetimeDisabled("Wlifetime-disabled",
static const cl::opt<bool> WarnLifetimeOutput("Wlifetime-output",
desc("Enforce output parameter validity check in all paths"), cl::init(false), cl::cat(CppSafeCategory));

static const cl::opt<bool> WarnLifetimeContainerMove("Wlifetime-container-move",
desc("Enable strict check on element move of containers"), cl::init(false), cl::cat(CppSafeCategory));

struct DetectSystemIncludesError : public std::runtime_error {
using std::runtime_error::runtime_error;
};
Expand Down Expand Up @@ -132,7 +129,6 @@ class LifetimeFrontendAction : public clang::ASTFrontendAction {
.LifetimeDisabled = WarnLifetimeDisabled,
.LifetimeGlobal = WarnLifetimeGlobal,
.LifetimeOutput = WarnLifetimeOutput,
.LifetimeContainerMove = WarnLifetimeContainerMove,
};

return std::make_unique<AstConsumer>(Options);
Expand Down