1//===----------------------------------------------------------------------===// 2// 3// The LLVM Compiler Infrastructure 4// 5// This file is dual licensed under the MIT and the University of Illinois Open 6// Source Licenses. See LICENSE.TXT for details. 7// 8//===----------------------------------------------------------------------===// 9 10// <mutex> 11 12// template <class L1, class L2, class... L3> 13// void lock(L1&, L2&, L3&...); 14 15#include <mutex> 16#include <cassert> 17 18class L0 19{ 20 bool locked_; 21 22public: 23 L0() : locked_(false) {} 24 25 void lock() 26 { 27 locked_ = true; 28 } 29 30 bool try_lock() 31 { 32 locked_ = true; 33 return locked_; 34 } 35 36 void unlock() {locked_ = false;} 37 38 bool locked() const {return locked_;} 39}; 40 41class L1 42{ 43 bool locked_; 44 45public: 46 L1() : locked_(false) {} 47 48 void lock() 49 { 50 locked_ = true; 51 } 52 53 bool try_lock() 54 { 55 locked_ = false; 56 return locked_; 57 } 58 59 void unlock() {locked_ = false;} 60 61 bool locked() const {return locked_;} 62}; 63 64class L2 65{ 66 bool locked_; 67 68public: 69 L2() : locked_(false) {} 70 71 void lock() 72 { 73 throw 1; 74 } 75 76 bool try_lock() 77 { 78 throw 1; 79 return locked_; 80 } 81 82 void unlock() {locked_ = false;} 83 84 bool locked() const {return locked_;} 85}; 86 87int main() 88{ 89 { 90 L0 l0; 91 L0 l1; 92 std::lock(l0, l1); 93 assert(l0.locked()); 94 assert(l1.locked()); 95 } 96 { 97 L0 l0; 98 L1 l1; 99 std::lock(l0, l1); 100 assert(l0.locked()); 101 assert(l1.locked()); 102 } 103 { 104 L1 l0; 105 L0 l1; 106 std::lock(l0, l1); 107 assert(l0.locked()); 108 assert(l1.locked()); 109 } 110 { 111 L0 l0; 112 L2 l1; 113 try 114 { 115 std::lock(l0, l1); 116 assert(false); 117 } 118 catch (int) 119 { 120 assert(!l0.locked()); 121 assert(!l1.locked()); 122 } 123 } 124 { 125 L2 l0; 126 L0 l1; 127 try 128 { 129 std::lock(l0, l1); 130 assert(false); 131 } 132 catch (int) 133 { 134 assert(!l0.locked()); 135 assert(!l1.locked()); 136 } 137 } 138 { 139 L1 l0; 140 L2 l1; 141 try 142 { 143 std::lock(l0, l1); 144 assert(false); 145 } 146 catch (int) 147 { 148 assert(!l0.locked()); 149 assert(!l1.locked()); 150 } 151 } 152 { 153 L2 l0; 154 L1 l1; 155 try 156 { 157 std::lock(l0, l1); 158 assert(false); 159 } 160 catch (int) 161 { 162 assert(!l0.locked()); 163 assert(!l1.locked()); 164 } 165 } 166 { 167 L2 l0; 168 L2 l1; 169 try 170 { 171 std::lock(l0, l1); 172 assert(false); 173 } 174 catch (int) 175 { 176 assert(!l0.locked()); 177 assert(!l1.locked()); 178 } 179 } 180#ifndef _LIBCPP_HAS_NO_VARIADICS 181 { 182 L0 l0; 183 L0 l1; 184 L0 l2; 185 std::lock(l0, l1, l2); 186 assert(l0.locked()); 187 assert(l1.locked()); 188 assert(l2.locked()); 189 } 190 { 191 L2 l0; 192 L2 l1; 193 L2 l2; 194 try 195 { 196 std::lock(l0, l1, l2); 197 assert(false); 198 } 199 catch (int) 200 { 201 assert(!l0.locked()); 202 assert(!l1.locked()); 203 assert(!l2.locked()); 204 } 205 } 206 { 207 L0 l0; 208 L0 l1; 209 L1 l2; 210 std::lock(l0, l1, l2); 211 assert(l0.locked()); 212 assert(l1.locked()); 213 assert(l2.locked()); 214 } 215 { 216 L0 l0; 217 L1 l1; 218 L0 l2; 219 std::lock(l0, l1, l2); 220 assert(l0.locked()); 221 assert(l1.locked()); 222 assert(l2.locked()); 223 } 224 { 225 L1 l0; 226 L0 l1; 227 L0 l2; 228 std::lock(l0, l1, l2); 229 assert(l0.locked()); 230 assert(l1.locked()); 231 assert(l2.locked()); 232 } 233 { 234 L0 l0; 235 L0 l1; 236 L2 l2; 237 try 238 { 239 std::lock(l0, l1, l2); 240 assert(false); 241 } 242 catch (int) 243 { 244 assert(!l0.locked()); 245 assert(!l1.locked()); 246 assert(!l2.locked()); 247 } 248 } 249 { 250 L0 l0; 251 L2 l1; 252 L0 l2; 253 try 254 { 255 std::lock(l0, l1, l2); 256 assert(false); 257 } 258 catch (int) 259 { 260 assert(!l0.locked()); 261 assert(!l1.locked()); 262 assert(!l2.locked()); 263 } 264 } 265 { 266 L2 l0; 267 L0 l1; 268 L0 l2; 269 try 270 { 271 std::lock(l0, l1, l2); 272 assert(false); 273 } 274 catch (int) 275 { 276 assert(!l0.locked()); 277 assert(!l1.locked()); 278 assert(!l2.locked()); 279 } 280 } 281 { 282 L2 l0; 283 L2 l1; 284 L0 l2; 285 try 286 { 287 std::lock(l0, l1, l2); 288 assert(false); 289 } 290 catch (int) 291 { 292 assert(!l0.locked()); 293 assert(!l1.locked()); 294 assert(!l2.locked()); 295 } 296 } 297 { 298 L2 l0; 299 L0 l1; 300 L2 l2; 301 try 302 { 303 std::lock(l0, l1, l2); 304 assert(false); 305 } 306 catch (int) 307 { 308 assert(!l0.locked()); 309 assert(!l1.locked()); 310 assert(!l2.locked()); 311 } 312 } 313 { 314 L0 l0; 315 L2 l1; 316 L2 l2; 317 try 318 { 319 std::lock(l0, l1, l2); 320 assert(false); 321 } 322 catch (int) 323 { 324 assert(!l0.locked()); 325 assert(!l1.locked()); 326 assert(!l2.locked()); 327 } 328 } 329 { 330 L2 l0; 331 L2 l1; 332 L1 l2; 333 try 334 { 335 std::lock(l0, l1, l2); 336 assert(false); 337 } 338 catch (int) 339 { 340 assert(!l0.locked()); 341 assert(!l1.locked()); 342 assert(!l2.locked()); 343 } 344 } 345 { 346 L2 l0; 347 L1 l1; 348 L2 l2; 349 try 350 { 351 std::lock(l0, l1, l2); 352 assert(false); 353 } 354 catch (int) 355 { 356 assert(!l0.locked()); 357 assert(!l1.locked()); 358 assert(!l2.locked()); 359 } 360 } 361 { 362 L1 l0; 363 L2 l1; 364 L2 l2; 365 try 366 { 367 std::lock(l0, l1, l2); 368 assert(false); 369 } 370 catch (int) 371 { 372 assert(!l0.locked()); 373 assert(!l1.locked()); 374 assert(!l2.locked()); 375 } 376 } 377 { 378 L0 l0; 379 L0 l1; 380 L0 l2; 381 L0 l3; 382 std::lock(l0, l1, l2, l3); 383 assert(l0.locked()); 384 assert(l1.locked()); 385 assert(l2.locked()); 386 assert(l3.locked()); 387 } 388 { 389 L0 l0; 390 L0 l1; 391 L0 l2; 392 L1 l3; 393 std::lock(l0, l1, l2, l3); 394 assert(l0.locked()); 395 assert(l1.locked()); 396 assert(l2.locked()); 397 assert(l3.locked()); 398 } 399 { 400 L0 l0; 401 L0 l1; 402 L1 l2; 403 L0 l3; 404 std::lock(l0, l1, l2, l3); 405 assert(l0.locked()); 406 assert(l1.locked()); 407 assert(l2.locked()); 408 assert(l3.locked()); 409 } 410 { 411 L0 l0; 412 L1 l1; 413 L0 l2; 414 L0 l3; 415 std::lock(l0, l1, l2, l3); 416 assert(l0.locked()); 417 assert(l1.locked()); 418 assert(l2.locked()); 419 assert(l3.locked()); 420 } 421 { 422 L1 l0; 423 L0 l1; 424 L0 l2; 425 L0 l3; 426 std::lock(l0, l1, l2, l3); 427 assert(l0.locked()); 428 assert(l1.locked()); 429 assert(l2.locked()); 430 assert(l3.locked()); 431 } 432 { 433 L0 l0; 434 L0 l1; 435 L0 l2; 436 L2 l3; 437 try 438 { 439 std::lock(l0, l1, l2, l3); 440 assert(false); 441 } 442 catch (int) 443 { 444 assert(!l0.locked()); 445 assert(!l1.locked()); 446 assert(!l2.locked()); 447 assert(!l3.locked()); 448 } 449 } 450 { 451 L0 l0; 452 L0 l1; 453 L2 l2; 454 L0 l3; 455 try 456 { 457 std::lock(l0, l1, l2, l3); 458 assert(false); 459 } 460 catch (int) 461 { 462 assert(!l0.locked()); 463 assert(!l1.locked()); 464 assert(!l2.locked()); 465 assert(!l3.locked()); 466 } 467 } 468 { 469 L0 l0; 470 L2 l1; 471 L0 l2; 472 L0 l3; 473 try 474 { 475 std::lock(l0, l1, l2, l3); 476 assert(false); 477 } 478 catch (int) 479 { 480 assert(!l0.locked()); 481 assert(!l1.locked()); 482 assert(!l2.locked()); 483 assert(!l3.locked()); 484 } 485 } 486 { 487 L2 l0; 488 L0 l1; 489 L0 l2; 490 L0 l3; 491 try 492 { 493 std::lock(l0, l1, l2, l3); 494 assert(false); 495 } 496 catch (int) 497 { 498 assert(!l0.locked()); 499 assert(!l1.locked()); 500 assert(!l2.locked()); 501 assert(!l3.locked()); 502 } 503 } 504#endif // _LIBCPP_HAS_NO_VARIADICS 505} 506