472 lines · cpp
1// RUN: %check_clang_tidy -std=c++17-or-later %s modernize-use-scoped-lock %t -- -- -isystem %clang_tidy_headers -fno-delayed-template-parsing2 3#include <mutex>4 5void Positive() {6 std::mutex m;7 {8 std::lock_guard<std::mutex> l(m);9 // CHECK-MESSAGES: :[[@LINE-1]]:5: warning: use 'std::scoped_lock' instead of 'std::lock_guard'10 // CHECK-FIXES: std::scoped_lock l(m);11 }12 13 {14 std::lock_guard<std::mutex> l(m, std::adopt_lock);15 // CHECK-MESSAGES: :[[@LINE-1]]:5: warning: use 'std::scoped_lock' instead of 'std::lock_guard'16 // CHECK-FIXES: std::scoped_lock l(std::adopt_lock, m);17 }18 19 {20 std::lock_guard<std::mutex> l1(m);21 std::lock_guard<std::mutex> l2(m);22 // CHECK-MESSAGES: :[[@LINE-2]]:5: warning: use single 'std::scoped_lock' instead of multiple 'std::lock_guard'23 // CHECK-MESSAGES: :[[@LINE-2]]:33: note: additional 'std::lock_guard' declared here24 }25 26 {27 std::lock_guard<std::mutex> l1(m), l2(m);28 // CHECK-MESSAGES: :[[@LINE-1]]:5: warning: use single 'std::scoped_lock' instead of multiple 'std::lock_guard'29 // CHECK-MESSAGES: :[[@LINE-2]]:40: note: additional 'std::lock_guard' declared here30 }31 32 {33 std::lock_guard<std::mutex> l1(m), l2(m), l3(m);34 std::lock_guard<std::mutex> l4(m);35 // CHECK-MESSAGES: :[[@LINE-2]]:5: warning: use single 'std::scoped_lock' instead of multiple 'std::lock_guard'36 // CHECK-MESSAGES: :[[@LINE-3]]:40: note: additional 'std::lock_guard' declared here37 // CHECK-MESSAGES: :[[@LINE-4]]:47: note: additional 'std::lock_guard' declared here38 // CHECK-MESSAGES: :[[@LINE-4]]:33: note: additional 'std::lock_guard' declared here39 }40 41 { 42 std::lock(m, m);43 std::lock_guard<std::mutex> l1(m, std::adopt_lock);44 std::lock_guard<std::mutex> l2(m, std::adopt_lock);45 // CHECK-MESSAGES: :[[@LINE-2]]:5: warning: use single 'std::scoped_lock' instead of multiple 'std::lock_guard'46 // CHECK-MESSAGES: :[[@LINE-2]]:33: note: additional 'std::lock_guard' declared here47 int a = 0;48 std::lock_guard<std::mutex> l3(m);49 // CHECK-MESSAGES: :[[@LINE-1]]:5: warning: use 'std::scoped_lock' instead of 'std::lock_guard'50 // CHECK-FIXES: std::scoped_lock l3(m);51 int b = 0;52 std::lock_guard<std::mutex> l4(m, std::adopt_lock);53 // CHECK-MESSAGES: :[[@LINE-1]]:5: warning: use 'std::scoped_lock' instead of 'std::lock_guard'54 // CHECK-FIXES: std::scoped_lock l4(std::adopt_lock, m);55 } 56}57 58 59std::mutex p_m1;60void PositiveShortFunction() {61 std::lock_guard<std::mutex> l(p_m1);62 // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use 'std::scoped_lock' instead of 'std::lock_guard'63 // CHECK-FIXES: std::scoped_lock l(p_m1);64}65 66 67void PositiveNested() {68 std::mutex m1;69 if (true) {70 std::lock_guard<std::mutex> l(m1);71 // CHECK-MESSAGES: :[[@LINE-1]]:5: warning: use 'std::scoped_lock' instead of 'std::lock_guard'72 // CHECK-FIXES: std::scoped_lock l(m1);73 {74 std::lock_guard<std::mutex> l2(m1);75 // CHECK-MESSAGES: :[[@LINE-1]]:7: warning: use 'std::scoped_lock' instead of 'std::lock_guard'76 // CHECK-FIXES: std::scoped_lock l2(m1);77 {78 std::lock_guard<std::mutex> l3(m1);79 std::lock_guard<std::mutex> l4(m1);80 // CHECK-MESSAGES: :[[@LINE-2]]:9: warning: use single 'std::scoped_lock' instead of multiple 'std::lock_guard'81 // CHECK-MESSAGES: :[[@LINE-2]]:37: note: additional 'std::lock_guard' declared here82 }83 {84 std::lock_guard<std::mutex> l2(m1);85 // CHECK-MESSAGES: :[[@LINE-1]]:9: warning: use 'std::scoped_lock' instead of 'std::lock_guard'86 // CHECK-FIXES: std::scoped_lock l2(m1);87 }88 }89 }90 std::lock_guard<std::mutex> l(m1);91 // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use 'std::scoped_lock' instead of 'std::lock_guard'92 // CHECK-FIXES: std::scoped_lock l(m1);93}94 95 96void PositiveInsideArg(std::mutex &m1, std::mutex &m2, std::mutex &m3) {97 std::lock_guard<std::mutex> l1(m1);98 std::lock_guard<std::mutex> l2(m2);99 // CHECK-MESSAGES: :[[@LINE-2]]:3: warning: use single 'std::scoped_lock' instead of multiple 'std::lock_guard'100 // CHECK-MESSAGES: :[[@LINE-2]]:31: note: additional 'std::lock_guard' declared here101 int a = 0;102 std::lock_guard<std::mutex> l3(m3);103 // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use 'std::scoped_lock' instead of 'std::lock_guard'104 // CHECK-FIXES: std::scoped_lock l3(m3);105}106 107 108void PositiveInsideConditional() {109 std::mutex m1;110 if (true) {111 std::lock_guard<std::mutex> l1(m1);112 // CHECK-MESSAGES: :[[@LINE-1]]:5: warning: use 'std::scoped_lock' instead of 'std::lock_guard'113 // CHECK-FIXES: std::scoped_lock l1(m1);114 } else {115 std::lock_guard<std::mutex> l1(m1);116 // CHECK-MESSAGES: :[[@LINE-1]]:5: warning: use 'std::scoped_lock' instead of 'std::lock_guard'117 // CHECK-FIXES: std::scoped_lock l1(m1);118 }119 120 while (true) {121 std::lock_guard<std::mutex> l1(m1);122 // CHECK-MESSAGES: :[[@LINE-1]]:5: warning: use 'std::scoped_lock' instead of 'std::lock_guard'123 // CHECK-FIXES: std::scoped_lock l1(m1);124 }125 126 for (int i = 0; i < 10; ++i) {127 std::lock_guard<std::mutex> l1(m1);128 // CHECK-MESSAGES: :[[@LINE-1]]:5: warning: use 'std::scoped_lock' instead of 'std::lock_guard'129 // CHECK-FIXES: std::scoped_lock l1(m1);130 }131}132 133void PositiveLambda() {134 std::mutex m;135 std::lock_guard<std::mutex> l1(m);136 // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use 'std::scoped_lock' instead of 'std::lock_guard'137 // CHECK-FIXES: std::scoped_lock l1(m);138 auto lambda1 = [&]() {139 std::lock_guard<std::mutex> l1(m);140 // CHECK-MESSAGES: :[[@LINE-1]]:5: warning: use 'std::scoped_lock' instead of 'std::lock_guard'141 // CHECK-FIXES: std::scoped_lock l1(m);142 };143 144 std::lock_guard<std::mutex> l3(m);145 std::lock_guard<std::mutex> l4(m);146 // CHECK-MESSAGES: :[[@LINE-2]]:3: warning: use single 'std::scoped_lock' instead of multiple 'std::lock_guard'147 // CHECK-MESSAGES: :[[@LINE-2]]:31: note: additional 'std::lock_guard' declared here148 auto lamda2 = [&]() {149 std::lock_guard<std::mutex> l3(m);150 std::lock_guard<std::mutex> l4(m);151 // CHECK-MESSAGES: :[[@LINE-2]]:5: warning: use single 'std::scoped_lock' instead of multiple 'std::lock_guard'152 // CHECK-MESSAGES: :[[@LINE-2]]:33: note: additional 'std::lock_guard' declared here153 };154 155 auto lamda3 = [&]() {156 std::lock(m, m);157 std::lock_guard<std::mutex> l1(m, std::adopt_lock);158 std::lock_guard<std::mutex> l2(m, std::adopt_lock);159 // CHECK-MESSAGES: :[[@LINE-2]]:5: warning: use single 'std::scoped_lock' instead of multiple 'std::lock_guard'160 // CHECK-MESSAGES: :[[@LINE-2]]:33: note: additional 'std::lock_guard' declared here161 int a = 0;162 std::lock_guard<std::mutex> l3(m);163 // CHECK-MESSAGES: :[[@LINE-1]]:5: warning: use 'std::scoped_lock' instead of 'std::lock_guard'164 // CHECK-FIXES: std::scoped_lock l3(m);165 int b = 0;166 std::lock_guard<std::mutex> l4(m, std::adopt_lock);167 // CHECK-MESSAGES: :[[@LINE-1]]:5: warning: use 'std::scoped_lock' instead of 'std::lock_guard'168 // CHECK-FIXES: std::scoped_lock l4(std::adopt_lock, m);169 };170 171 auto lamda4 = [&]() {172 std::lock_guard<std::mutex> l1(m);173 // CHECK-MESSAGES: :[[@LINE-1]]:5: warning: use 'std::scoped_lock' instead of 'std::lock_guard'174 // CHECK-FIXES: std::scoped_lock l1(m);175 int a = 0;176 std::lock_guard<std::mutex> l2(m);177 // CHECK-MESSAGES: :[[@LINE-1]]:5: warning: use 'std::scoped_lock' instead of 'std::lock_guard'178 // CHECK-FIXES: std::scoped_lock l2(m);179 };180}181 182template <typename T>183void PositiveTemplated() {184 std::mutex m1, m2, m3;185 {186 std::lock_guard<std::mutex> l(m1);187 // CHECK-MESSAGES: :[[@LINE-1]]:5: warning: use 'std::scoped_lock' instead of 'std::lock_guard'188 // CHECK-FIXES: std::scoped_lock l(m1);189 }190 191 {192 std::lock_guard<std::mutex> l1(m1);193 std::lock_guard<std::mutex> l2(m2);194 // CHECK-MESSAGES: :[[@LINE-2]]:5: warning: use single 'std::scoped_lock' instead of multiple 'std::lock_guard'195 // CHECK-MESSAGES: :[[@LINE-2]]:33: note: additional 'std::lock_guard' declared here196 }197 198 {199 std::lock(m1, m2);200 std::lock_guard<std::mutex> l1(m1, std::adopt_lock);201 std::lock_guard<std::mutex> l2(m2, std::adopt_lock);202 // CHECK-MESSAGES: :[[@LINE-2]]:5: warning: use single 'std::scoped_lock' instead of multiple 'std::lock_guard'203 // CHECK-MESSAGES: :[[@LINE-2]]:33: note: additional 'std::lock_guard' declared here204 int a = 0;205 std::lock_guard<std::mutex> l3(m3);206 // CHECK-MESSAGES: :[[@LINE-1]]:5: warning: use 'std::scoped_lock' instead of 'std::lock_guard'207 // CHECK-FIXES: std::scoped_lock l3(m3);208 }209}210 211 212template <typename Mutex>213void PositiveTemplatedMutex() {214 Mutex m1, m2, m3;215 {216 std::lock_guard<Mutex> l(m1);217 // CHECK-MESSAGES: :[[@LINE-1]]:5: warning: use 'std::scoped_lock' instead of 'std::lock_guard'218 }219 220 {221 std::lock_guard<Mutex> l1(m1);222 std::lock_guard<Mutex> l2(m2);223 // CHECK-MESSAGES: :[[@LINE-2]]:5: warning: use single 'std::scoped_lock' instead of multiple 'std::lock_guard'224 // CHECK-MESSAGES: :[[@LINE-2]]:28: note: additional 'std::lock_guard' declared here225 }226 227 {228 std::lock(m1, m2);229 std::lock_guard<Mutex> l1(m1, std::adopt_lock);230 std::lock_guard<Mutex> l2(m2, std::adopt_lock);231 // CHECK-MESSAGES: :[[@LINE-2]]:5: warning: use single 'std::scoped_lock' instead of multiple 'std::lock_guard'232 // CHECK-MESSAGES: :[[@LINE-2]]:28: note: additional 'std::lock_guard' declared here233 int a = 0;234 std::lock_guard<Mutex> l3(m3);235 // CHECK-MESSAGES: :[[@LINE-1]]:5: warning: use 'std::scoped_lock' instead of 'std::lock_guard'236 }237}238 239 240template <template <typename> typename Lock>241void NegativeTemplate() {242 std::mutex m1, m2;243 {244 Lock<std::mutex> l(m1);245 }246 247 {248 Lock<std::mutex> l1(m1);249 Lock<std::mutex> l2(m2);250 }251}252 253void instantiate() {254 NegativeTemplate<std::lock_guard>();255}256 257 258struct PositiveClass {259 void Positive() {260 {261 std::lock_guard<std::mutex> l(m1);262 // CHECK-MESSAGES: :[[@LINE-1]]:7: warning: use 'std::scoped_lock' instead of 'std::lock_guard'263 // CHECK-FIXES: std::scoped_lock l(m1);264 }265 266 {267 std::lock_guard<std::mutex> l1(m1);268 std::lock_guard<std::mutex> l2(m2);269 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: use single 'std::scoped_lock' instead of multiple 'std::lock_guard'270 // CHECK-MESSAGES: :[[@LINE-2]]:35: note: additional 'std::lock_guard' declared here271 }272 273 {274 std::lock(m1, m2); 275 std::lock_guard<std::mutex> l1(m1, std::adopt_lock);276 std::lock_guard<std::mutex> l2(m2, std::adopt_lock);277 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: use single 'std::scoped_lock' instead of multiple 'std::lock_guard'278 // CHECK-MESSAGES: :[[@LINE-2]]:35: note: additional 'std::lock_guard' declared here279 int a = 0;280 std::lock_guard<std::mutex> l3(m3);281 // CHECK-MESSAGES: :[[@LINE-1]]:7: warning: use 'std::scoped_lock' instead of 'std::lock_guard'282 // CHECK-FIXES: std::scoped_lock l3(m3);283 }284 }285 286 std::mutex m1;287 std::mutex m2;288 std::mutex m3;289};290 291 292template <typename T>293struct PositiveTemplatedClass {294 void Positive() {295 {296 std::lock_guard<std::mutex> l(m1);297 // CHECK-MESSAGES: :[[@LINE-1]]:7: warning: use 'std::scoped_lock' instead of 'std::lock_guard'298 // CHECK-FIXES: std::scoped_lock l(m1);299 }300 301 {302 std::lock(m1, m2); 303 std::lock_guard<std::mutex> l1(m1, std::adopt_lock);304 std::lock_guard<std::mutex> l2(m2, std::adopt_lock);305 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: use single 'std::scoped_lock' instead of multiple 'std::lock_guard'306 // CHECK-MESSAGES: :[[@LINE-2]]:35: note: additional 'std::lock_guard' declared here307 int a = 0;308 std::lock_guard<std::mutex> l3(m3);309 // CHECK-MESSAGES: :[[@LINE-1]]:7: warning: use 'std::scoped_lock' instead of 'std::lock_guard'310 // CHECK-FIXES: std::scoped_lock l3(m3);311 }312 }313 314 template <typename... Ts>315 void TemplatedPositive() {316 {317 std::lock_guard<std::mutex> l(m1);318 // CHECK-MESSAGES: :[[@LINE-1]]:7: warning: use 'std::scoped_lock' instead of 'std::lock_guard'319 // CHECK-FIXES: std::scoped_lock l(m1);320 }321 322 {323 std::lock(m1, m2); 324 std::lock_guard<std::mutex> l1(m1, std::adopt_lock);325 std::lock_guard<std::mutex> l2(m2, std::adopt_lock);326 // CHECK-MESSAGES: :[[@LINE-2]]:7: warning: use single 'std::scoped_lock' instead of multiple 'std::lock_guard'327 // CHECK-MESSAGES: :[[@LINE-2]]:35: note: additional 'std::lock_guard' declared here328 int a = 0;329 std::lock_guard<std::mutex> l3(m3);330 // CHECK-MESSAGES: :[[@LINE-1]]:7: warning: use 'std::scoped_lock' instead of 'std::lock_guard'331 // CHECK-FIXES: std::scoped_lock l3(m3);332 }333 }334 335 std::mutex m1;336 std::mutex m2;337 std::mutex m3;338};339 340 341template <typename T>342using Lock = std::lock_guard<T>;343// CHECK-MESSAGES: :[[@LINE-1]]:14: warning: use 'std::scoped_lock' instead of 'std::lock_guard'344// CHECK-FIXES: using Lock = std::scoped_lock<T>;345 346using LockM = std::lock_guard<std::mutex>;347// CHECK-MESSAGES: :[[@LINE-1]]:15: warning: use 'std::scoped_lock' instead of 'std::lock_guard'348// CHECK-FIXES: using LockM = std::scoped_lock<std::mutex>;349 350typedef std::lock_guard<std::mutex> LockDef;351// CHECK-MESSAGES: :[[@LINE-1]]:9: warning: use 'std::scoped_lock' instead of 'std::lock_guard'352// CHECK-FIXES: typedef std::scoped_lock<std::mutex> LockDef;353 354 355void PositiveUsingDecl() {356 using std::lock_guard;357 // CHECK-MESSAGES: :[[@LINE-1]]:14: warning: use 'std::scoped_lock' instead of 'std::lock_guard'358 // CHECK-FIXES: using std::scoped_lock;359 360 using LockMFun = std::lock_guard<std::mutex>;361 // CHECK-MESSAGES: :[[@LINE-1]]:20: warning: use 'std::scoped_lock' instead of 'std::lock_guard'362 // CHECK-FIXES: using LockMFun = std::scoped_lock<std::mutex>;363 364 typedef std::lock_guard<std::mutex> LockDefFun;365 // CHECK-MESSAGES: :[[@LINE-1]]:11: warning: use 'std::scoped_lock' instead of 'std::lock_guard'366 // CHECK-FIXES: typedef std::scoped_lock<std::mutex> LockDefFun;367}368 369template <typename T>370void PositiveUsingDeclTemplate() {371 using std::lock_guard;372 // CHECK-MESSAGES: :[[@LINE-1]]:14: warning: use 'std::scoped_lock' instead of 'std::lock_guard'373 // CHECK-FIXES: using std::scoped_lock;374 375 std::mutex m;376 lock_guard<std::mutex> l(m);377 // CHECK-MESSAGES: :[[@LINE-1]]:3: warning: use 'std::scoped_lock' instead of 'std::lock_guard'378 // CHECK-FIXES: std::scoped_lock l(m);379 380 using LockFunT = std::lock_guard<T>;381 // CHECK-MESSAGES: :[[@LINE-1]]:20: warning: use 'std::scoped_lock' instead of 'std::lock_guard'382 // CHECK-FIXES: using LockFunT = std::scoped_lock<T>;383 384 using LockMFunT = std::lock_guard<std::mutex>;385 // CHECK-MESSAGES: :[[@LINE-1]]:21: warning: use 'std::scoped_lock' instead of 'std::lock_guard'386 // CHECK-FIXES: using LockMFunT = std::scoped_lock<std::mutex>;387 388 typedef std::lock_guard<std::mutex> LockDefFunT;389 // CHECK-MESSAGES: :[[@LINE-1]]:11: warning: use 'std::scoped_lock' instead of 'std::lock_guard'390 // CHECK-FIXES: typedef std::scoped_lock<std::mutex> LockDefFunT;391}392 393void PositiveInUsingTypedefs() {394 std::mutex m;395 396 {397 Lock<std::mutex> l(m);398 // CHECK-MESSAGES: :[[@LINE-1]]:5: warning: use 'std::scoped_lock' instead of 'std::lock_guard'399 // CHECK-FIXES: std::scoped_lock l(m);400 }401 402 {403 LockM l(m);404 // CHECK-MESSAGES: :[[@LINE-1]]:5: warning: use 'std::scoped_lock' instead of 'std::lock_guard'405 // CHECK-FIXES: std::scoped_lock l(m);406 }407 408 {409 LockDef l(m);410 // CHECK-MESSAGES: :[[@LINE-1]]:5: warning: use 'std::scoped_lock' instead of 'std::lock_guard'411 // CHECK-FIXES: std::scoped_lock l(m);412 }413 414 {415 std::lock(m, m);416 Lock<std::mutex> l1(m, std::adopt_lock);417 LockM l2(m, std::adopt_lock);418 LockDef l3(m), l4(m);419 // CHECK-MESSAGES: :[[@LINE-3]]:5: warning: use single 'std::scoped_lock' instead of multiple 'std::lock_guard'420 // CHECK-MESSAGES: :[[@LINE-3]]:11: note: additional 'std::lock_guard' declared here421 // CHECK-MESSAGES: :[[@LINE-3]]:13: note: additional 'std::lock_guard' declared here422 // CHECK-MESSAGES: :[[@LINE-4]]:20: note: additional 'std::lock_guard' declared here423 int a = 0;424 LockDef l5(m);425 // CHECK-MESSAGES: :[[@LINE-1]]:5: warning: use 'std::scoped_lock' instead of 'std::lock_guard'426 // CHECK-FIXES: std::scoped_lock l5(m);427 }428}429 430template <typename Mutex>431void PositiveInUsingTypedefsTemplated() {432 Mutex m;433 434 {435 Lock<Mutex> l(m);436 // CHECK-MESSAGES: :[[@LINE-1]]:5: warning: use 'std::scoped_lock' instead of 'std::lock_guard'437 }438 439 {440 std::lock(m, m);441 Lock<Mutex> l1(m, std::adopt_lock);442 LockM l2(m, std::adopt_lock);443 LockDef l3(m), l4(m);444 // CHECK-MESSAGES: :[[@LINE-3]]:5: warning: use single 'std::scoped_lock' instead of multiple 'std::lock_guard'445 // CHECK-MESSAGES: :[[@LINE-3]]:11: note: additional 'std::lock_guard' declared here446 // CHECK-MESSAGES: :[[@LINE-3]]:13: note: additional 'std::lock_guard' declared here447 // CHECK-MESSAGES: :[[@LINE-4]]:20: note: additional 'std::lock_guard' declared here448 int a = 0;449 LockDef l5(m);450 // CHECK-MESSAGES: :[[@LINE-1]]:5: warning: use 'std::scoped_lock' instead of 'std::lock_guard'451 }452}453 454// Non-STD lock_guard.455template <typename Mutex>456struct lock_guard {457 lock_guard(Mutex &m) { }458 lock_guard(const lock_guard& ) = delete;459};460 461void NegativeNonStdLockGuard() {462 std::mutex m;463 {464 lock_guard<std::mutex> l(m);465 }466 467 {468 lock_guard<std::mutex> l1(m);469 lock_guard<std::mutex> l2(m);470 }471}472