1 // SPDX-License-Identifier: GPL-2.0-only 1 // SPDX-License-Identifier: GPL-2.0-only 2 /// Find missing unlocks. This semantic match 2 /// Find missing unlocks. This semantic match considers the specific case 3 /// where the unlock is missing from an if bra 3 /// where the unlock is missing from an if branch, and there is a lock 4 /// before the if and an unlock after the if. 4 /// before the if and an unlock after the if. False positives are due to 5 /// cases where the if branch represents a cas 5 /// cases where the if branch represents a case where the function is 6 /// supposed to exit with the lock held, or wh 6 /// supposed to exit with the lock held, or where there is some preceding 7 /// function call that releases the lock. 7 /// function call that releases the lock. 8 /// 8 /// 9 // Confidence: Moderate 9 // Confidence: Moderate 10 // Copyright: (C) 2010-2012 Nicolas Palix. 10 // Copyright: (C) 2010-2012 Nicolas Palix. 11 // Copyright: (C) 2010-2012 Julia Lawall, INRI 11 // Copyright: (C) 2010-2012 Julia Lawall, INRIA/LIP6. 12 // Copyright: (C) 2010-2012 Gilles Muller, INR 12 // Copyright: (C) 2010-2012 Gilles Muller, INRIA/LiP6. 13 // URL: https://coccinelle.gitlabpages.inria.f 13 // URL: https://coccinelle.gitlabpages.inria.fr/website 14 // Comments: 14 // Comments: 15 // Options: --no-includes --include-headers 15 // Options: --no-includes --include-headers 16 16 17 virtual context 17 virtual context 18 virtual org 18 virtual org 19 virtual report 19 virtual report 20 20 21 @prelocked@ 21 @prelocked@ 22 position p1,p; 22 position p1,p; 23 expression E1; 23 expression E1; 24 @@ 24 @@ 25 25 26 ( 26 ( 27 mutex_lock@p1 27 mutex_lock@p1 28 | 28 | 29 mutex_trylock@p1 29 mutex_trylock@p1 30 | 30 | 31 spin_lock@p1 31 spin_lock@p1 32 | 32 | 33 spin_trylock@p1 33 spin_trylock@p1 34 | 34 | 35 read_lock@p1 35 read_lock@p1 36 | 36 | 37 read_trylock@p1 37 read_trylock@p1 38 | 38 | 39 write_lock@p1 39 write_lock@p1 40 | 40 | 41 write_trylock@p1 41 write_trylock@p1 42 | 42 | 43 read_lock_irq@p1 43 read_lock_irq@p1 44 | 44 | 45 write_lock_irq@p1 45 write_lock_irq@p1 46 | 46 | 47 read_lock_irqsave@p1 47 read_lock_irqsave@p1 48 | 48 | 49 write_lock_irqsave@p1 49 write_lock_irqsave@p1 50 | 50 | 51 spin_lock_irq@p1 51 spin_lock_irq@p1 52 | 52 | 53 spin_lock_irqsave@p1 53 spin_lock_irqsave@p1 54 ) (E1@p,...); 54 ) (E1@p,...); 55 55 56 @looped@ 56 @looped@ 57 position r; 57 position r; 58 @@ 58 @@ 59 59 60 for(...;...;...) { <+... return@r ...; ...+> } 60 for(...;...;...) { <+... return@r ...; ...+> } 61 61 62 @err exists@ 62 @err exists@ 63 expression E1; 63 expression E1; 64 position prelocked.p; 64 position prelocked.p; 65 position up != prelocked.p1; 65 position up != prelocked.p1; 66 position r!=looped.r; 66 position r!=looped.r; 67 identifier lock,unlock; 67 identifier lock,unlock; 68 @@ 68 @@ 69 69 70 *lock(E1@p,...); 70 *lock(E1@p,...); 71 ... when != E1 71 ... when != E1 72 when any 72 when any 73 if (...) { 73 if (...) { 74 ... when != E1 74 ... when != E1 75 * return@r ...; 75 * return@r ...; 76 } 76 } 77 ... when != E1 77 ... when != E1 78 when any 78 when any 79 *unlock@up(E1,...); 79 *unlock@up(E1,...); 80 80 81 @script:python depends on org@ 81 @script:python depends on org@ 82 p << prelocked.p1; 82 p << prelocked.p1; 83 lock << err.lock; 83 lock << err.lock; 84 unlock << err.unlock; 84 unlock << err.unlock; 85 p2 << err.r; 85 p2 << err.r; 86 @@ 86 @@ 87 87 88 cocci.print_main(lock,p) 88 cocci.print_main(lock,p) 89 cocci.print_secs(unlock,p2) 89 cocci.print_secs(unlock,p2) 90 90 91 @script:python depends on report@ 91 @script:python depends on report@ 92 p << prelocked.p1; 92 p << prelocked.p1; 93 lock << err.lock; 93 lock << err.lock; 94 unlock << err.unlock; 94 unlock << err.unlock; 95 p2 << err.r; 95 p2 << err.r; 96 @@ 96 @@ 97 97 98 msg = "preceding lock on line %s" % (p[0].line 98 msg = "preceding lock on line %s" % (p[0].line) 99 coccilib.report.print_report(p2[0],msg) 99 coccilib.report.print_report(p2[0],msg)
Linux® is a registered trademark of Linus Torvalds in the United States and other countries.
TOMOYO® is a registered trademark of NTT DATA CORPORATION.