.. | .. |
---|
28 | 28 | * Change this to 1 if you want to see the failure printouts: |
---|
29 | 29 | */ |
---|
30 | 30 | static unsigned int debug_locks_verbose; |
---|
| 31 | +unsigned int force_read_lock_recursive; |
---|
31 | 32 | |
---|
32 | 33 | static DEFINE_WD_CLASS(ww_lockdep); |
---|
33 | 34 | |
---|
.. | .. |
---|
185 | 186 | #define HARDIRQ_ENTER() \ |
---|
186 | 187 | local_irq_disable(); \ |
---|
187 | 188 | __irq_enter(); \ |
---|
| 189 | + lockdep_hardirq_threaded(); \ |
---|
188 | 190 | WARN_ON(!in_irq()); |
---|
189 | 191 | |
---|
190 | 192 | #define HARDIRQ_EXIT() \ |
---|
.. | .. |
---|
393 | 395 | WSL(X1); |
---|
394 | 396 | WSU(X1); |
---|
395 | 397 | MU(Y1); // should fail |
---|
| 398 | +} |
---|
| 399 | + |
---|
| 400 | +/* |
---|
| 401 | + * read_lock(A) |
---|
| 402 | + * spin_lock(B) |
---|
| 403 | + * spin_lock(B) |
---|
| 404 | + * write_lock(A) |
---|
| 405 | + * |
---|
| 406 | + * This test case is aimed at poking whether the chain cache prevents us from |
---|
| 407 | + * detecting a read-lock/lock-write deadlock: if the chain cache doesn't differ |
---|
| 408 | + * read/write locks, the following case may happen |
---|
| 409 | + * |
---|
| 410 | + * { read_lock(A)->lock(B) dependency exists } |
---|
| 411 | + * |
---|
| 412 | + * P0: |
---|
| 413 | + * lock(B); |
---|
| 414 | + * read_lock(A); |
---|
| 415 | + * |
---|
| 416 | + * { Not a deadlock, B -> A is added in the chain cache } |
---|
| 417 | + * |
---|
| 418 | + * P1: |
---|
| 419 | + * lock(B); |
---|
| 420 | + * write_lock(A); |
---|
| 421 | + * |
---|
| 422 | + * { B->A found in chain cache, not reported as a deadlock } |
---|
| 423 | + * |
---|
| 424 | + */ |
---|
| 425 | +static void rlock_chaincache_ABBA1(void) |
---|
| 426 | +{ |
---|
| 427 | + RL(X1); |
---|
| 428 | + L(Y1); |
---|
| 429 | + U(Y1); |
---|
| 430 | + RU(X1); |
---|
| 431 | + |
---|
| 432 | + L(Y1); |
---|
| 433 | + RL(X1); |
---|
| 434 | + RU(X1); |
---|
| 435 | + U(Y1); |
---|
| 436 | + |
---|
| 437 | + L(Y1); |
---|
| 438 | + WL(X1); |
---|
| 439 | + WU(X1); |
---|
| 440 | + U(Y1); // should fail |
---|
396 | 441 | } |
---|
397 | 442 | |
---|
398 | 443 | /* |
---|
.. | .. |
---|
742 | 787 | #include "locking-selftest-spin-hardirq.h" |
---|
743 | 788 | GENERATE_PERMUTATIONS_2_EVENTS(irqsafe1_hard_spin) |
---|
744 | 789 | |
---|
745 | | -#ifndef CONFIG_PREEMPT_RT_FULL |
---|
746 | | - |
---|
747 | 790 | #include "locking-selftest-rlock-hardirq.h" |
---|
748 | 791 | GENERATE_PERMUTATIONS_2_EVENTS(irqsafe1_hard_rlock) |
---|
749 | 792 | |
---|
.. | .. |
---|
759 | 802 | #include "locking-selftest-wlock-softirq.h" |
---|
760 | 803 | GENERATE_PERMUTATIONS_2_EVENTS(irqsafe1_soft_wlock) |
---|
761 | 804 | |
---|
762 | | -#endif |
---|
763 | | - |
---|
764 | 805 | #undef E1 |
---|
765 | 806 | #undef E2 |
---|
766 | 807 | |
---|
767 | | -#ifndef CONFIG_PREEMPT_RT_FULL |
---|
768 | 808 | /* |
---|
769 | 809 | * Enabling hardirqs with a softirq-safe lock held: |
---|
770 | 810 | */ |
---|
.. | .. |
---|
797 | 837 | #undef E1 |
---|
798 | 838 | #undef E2 |
---|
799 | 839 | |
---|
800 | | -#endif |
---|
801 | | - |
---|
802 | 840 | /* |
---|
803 | 841 | * Enabling irqs with an irq-safe lock held: |
---|
804 | 842 | */ |
---|
.. | .. |
---|
822 | 860 | #include "locking-selftest-spin-hardirq.h" |
---|
823 | 861 | GENERATE_PERMUTATIONS_2_EVENTS(irqsafe2B_hard_spin) |
---|
824 | 862 | |
---|
825 | | -#ifndef CONFIG_PREEMPT_RT_FULL |
---|
826 | | - |
---|
827 | 863 | #include "locking-selftest-rlock-hardirq.h" |
---|
828 | 864 | GENERATE_PERMUTATIONS_2_EVENTS(irqsafe2B_hard_rlock) |
---|
829 | 865 | |
---|
.. | .. |
---|
838 | 874 | |
---|
839 | 875 | #include "locking-selftest-wlock-softirq.h" |
---|
840 | 876 | GENERATE_PERMUTATIONS_2_EVENTS(irqsafe2B_soft_wlock) |
---|
841 | | - |
---|
842 | | -#endif |
---|
843 | 877 | |
---|
844 | 878 | #undef E1 |
---|
845 | 879 | #undef E2 |
---|
.. | .. |
---|
872 | 906 | #include "locking-selftest-spin-hardirq.h" |
---|
873 | 907 | GENERATE_PERMUTATIONS_3_EVENTS(irqsafe3_hard_spin) |
---|
874 | 908 | |
---|
875 | | -#ifndef CONFIG_PREEMPT_RT_FULL |
---|
876 | | - |
---|
877 | 909 | #include "locking-selftest-rlock-hardirq.h" |
---|
878 | 910 | GENERATE_PERMUTATIONS_3_EVENTS(irqsafe3_hard_rlock) |
---|
879 | 911 | |
---|
.. | .. |
---|
888 | 920 | |
---|
889 | 921 | #include "locking-selftest-wlock-softirq.h" |
---|
890 | 922 | GENERATE_PERMUTATIONS_3_EVENTS(irqsafe3_soft_wlock) |
---|
891 | | - |
---|
892 | | -#endif |
---|
893 | 923 | |
---|
894 | 924 | #undef E1 |
---|
895 | 925 | #undef E2 |
---|
.. | .. |
---|
924 | 954 | #include "locking-selftest-spin-hardirq.h" |
---|
925 | 955 | GENERATE_PERMUTATIONS_3_EVENTS(irqsafe4_hard_spin) |
---|
926 | 956 | |
---|
927 | | -#ifndef CONFIG_PREEMPT_RT_FULL |
---|
928 | | - |
---|
929 | 957 | #include "locking-selftest-rlock-hardirq.h" |
---|
930 | 958 | GENERATE_PERMUTATIONS_3_EVENTS(irqsafe4_hard_rlock) |
---|
931 | 959 | |
---|
.. | .. |
---|
941 | 969 | #include "locking-selftest-wlock-softirq.h" |
---|
942 | 970 | GENERATE_PERMUTATIONS_3_EVENTS(irqsafe4_soft_wlock) |
---|
943 | 971 | |
---|
944 | | -#endif |
---|
945 | | - |
---|
946 | 972 | #undef E1 |
---|
947 | 973 | #undef E2 |
---|
948 | 974 | #undef E3 |
---|
949 | | - |
---|
950 | | -#ifndef CONFIG_PREEMPT_RT_FULL |
---|
951 | 975 | |
---|
952 | 976 | /* |
---|
953 | 977 | * read-lock / write-lock irq inversion. |
---|
.. | .. |
---|
1011 | 1035 | #undef E2 |
---|
1012 | 1036 | #undef E3 |
---|
1013 | 1037 | |
---|
1014 | | -#endif |
---|
| 1038 | +/* |
---|
| 1039 | + * write-read / write-read / write-read deadlock even if read is recursive |
---|
| 1040 | + */ |
---|
1015 | 1041 | |
---|
1016 | | -#ifndef CONFIG_PREEMPT_RT_FULL |
---|
| 1042 | +#define E1() \ |
---|
| 1043 | + \ |
---|
| 1044 | + WL(X1); \ |
---|
| 1045 | + RL(Y1); \ |
---|
| 1046 | + RU(Y1); \ |
---|
| 1047 | + WU(X1); |
---|
1017 | 1048 | |
---|
| 1049 | +#define E2() \ |
---|
| 1050 | + \ |
---|
| 1051 | + WL(Y1); \ |
---|
| 1052 | + RL(Z1); \ |
---|
| 1053 | + RU(Z1); \ |
---|
| 1054 | + WU(Y1); |
---|
| 1055 | + |
---|
| 1056 | +#define E3() \ |
---|
| 1057 | + \ |
---|
| 1058 | + WL(Z1); \ |
---|
| 1059 | + RL(X1); \ |
---|
| 1060 | + RU(X1); \ |
---|
| 1061 | + WU(Z1); |
---|
| 1062 | + |
---|
| 1063 | +#include "locking-selftest-rlock.h" |
---|
| 1064 | +GENERATE_PERMUTATIONS_3_EVENTS(W1R2_W2R3_W3R1) |
---|
| 1065 | + |
---|
| 1066 | +#undef E1 |
---|
| 1067 | +#undef E2 |
---|
| 1068 | +#undef E3 |
---|
| 1069 | + |
---|
| 1070 | +/* |
---|
| 1071 | + * write-write / read-read / write-read deadlock even if read is recursive |
---|
| 1072 | + */ |
---|
| 1073 | + |
---|
| 1074 | +#define E1() \ |
---|
| 1075 | + \ |
---|
| 1076 | + WL(X1); \ |
---|
| 1077 | + WL(Y1); \ |
---|
| 1078 | + WU(Y1); \ |
---|
| 1079 | + WU(X1); |
---|
| 1080 | + |
---|
| 1081 | +#define E2() \ |
---|
| 1082 | + \ |
---|
| 1083 | + RL(Y1); \ |
---|
| 1084 | + RL(Z1); \ |
---|
| 1085 | + RU(Z1); \ |
---|
| 1086 | + RU(Y1); |
---|
| 1087 | + |
---|
| 1088 | +#define E3() \ |
---|
| 1089 | + \ |
---|
| 1090 | + WL(Z1); \ |
---|
| 1091 | + RL(X1); \ |
---|
| 1092 | + RU(X1); \ |
---|
| 1093 | + WU(Z1); |
---|
| 1094 | + |
---|
| 1095 | +#include "locking-selftest-rlock.h" |
---|
| 1096 | +GENERATE_PERMUTATIONS_3_EVENTS(W1W2_R2R3_W3R1) |
---|
| 1097 | + |
---|
| 1098 | +#undef E1 |
---|
| 1099 | +#undef E2 |
---|
| 1100 | +#undef E3 |
---|
| 1101 | + |
---|
| 1102 | +/* |
---|
| 1103 | + * write-write / read-read / read-write is not deadlock when read is recursive |
---|
| 1104 | + */ |
---|
| 1105 | + |
---|
| 1106 | +#define E1() \ |
---|
| 1107 | + \ |
---|
| 1108 | + WL(X1); \ |
---|
| 1109 | + WL(Y1); \ |
---|
| 1110 | + WU(Y1); \ |
---|
| 1111 | + WU(X1); |
---|
| 1112 | + |
---|
| 1113 | +#define E2() \ |
---|
| 1114 | + \ |
---|
| 1115 | + RL(Y1); \ |
---|
| 1116 | + RL(Z1); \ |
---|
| 1117 | + RU(Z1); \ |
---|
| 1118 | + RU(Y1); |
---|
| 1119 | + |
---|
| 1120 | +#define E3() \ |
---|
| 1121 | + \ |
---|
| 1122 | + RL(Z1); \ |
---|
| 1123 | + WL(X1); \ |
---|
| 1124 | + WU(X1); \ |
---|
| 1125 | + RU(Z1); |
---|
| 1126 | + |
---|
| 1127 | +#include "locking-selftest-rlock.h" |
---|
| 1128 | +GENERATE_PERMUTATIONS_3_EVENTS(W1R2_R2R3_W3W1) |
---|
| 1129 | + |
---|
| 1130 | +#undef E1 |
---|
| 1131 | +#undef E2 |
---|
| 1132 | +#undef E3 |
---|
| 1133 | + |
---|
| 1134 | +/* |
---|
| 1135 | + * write-read / read-read / write-write is not deadlock when read is recursive |
---|
| 1136 | + */ |
---|
| 1137 | + |
---|
| 1138 | +#define E1() \ |
---|
| 1139 | + \ |
---|
| 1140 | + WL(X1); \ |
---|
| 1141 | + RL(Y1); \ |
---|
| 1142 | + RU(Y1); \ |
---|
| 1143 | + WU(X1); |
---|
| 1144 | + |
---|
| 1145 | +#define E2() \ |
---|
| 1146 | + \ |
---|
| 1147 | + RL(Y1); \ |
---|
| 1148 | + RL(Z1); \ |
---|
| 1149 | + RU(Z1); \ |
---|
| 1150 | + RU(Y1); |
---|
| 1151 | + |
---|
| 1152 | +#define E3() \ |
---|
| 1153 | + \ |
---|
| 1154 | + WL(Z1); \ |
---|
| 1155 | + WL(X1); \ |
---|
| 1156 | + WU(X1); \ |
---|
| 1157 | + WU(Z1); |
---|
| 1158 | + |
---|
| 1159 | +#include "locking-selftest-rlock.h" |
---|
| 1160 | +GENERATE_PERMUTATIONS_3_EVENTS(W1W2_R2R3_R3W1) |
---|
| 1161 | + |
---|
| 1162 | +#undef E1 |
---|
| 1163 | +#undef E2 |
---|
| 1164 | +#undef E3 |
---|
1018 | 1165 | /* |
---|
1019 | 1166 | * read-lock / write-lock recursion that is actually safe. |
---|
1020 | 1167 | */ |
---|
.. | .. |
---|
1034 | 1181 | #define E3() \ |
---|
1035 | 1182 | \ |
---|
1036 | 1183 | IRQ_ENTER(); \ |
---|
1037 | | - RL(A); \ |
---|
| 1184 | + LOCK(A); \ |
---|
1038 | 1185 | L(B); \ |
---|
1039 | 1186 | U(B); \ |
---|
1040 | | - RU(A); \ |
---|
| 1187 | + UNLOCK(A); \ |
---|
1041 | 1188 | IRQ_EXIT(); |
---|
1042 | 1189 | |
---|
1043 | 1190 | /* |
---|
1044 | | - * Generate 12 testcases: |
---|
| 1191 | + * Generate 24 testcases: |
---|
1045 | 1192 | */ |
---|
1046 | 1193 | #include "locking-selftest-hardirq.h" |
---|
1047 | | -GENERATE_PERMUTATIONS_3_EVENTS(irq_read_recursion_hard) |
---|
| 1194 | +#include "locking-selftest-rlock.h" |
---|
| 1195 | +GENERATE_PERMUTATIONS_3_EVENTS(irq_read_recursion_hard_rlock) |
---|
| 1196 | + |
---|
| 1197 | +#include "locking-selftest-wlock.h" |
---|
| 1198 | +GENERATE_PERMUTATIONS_3_EVENTS(irq_read_recursion_hard_wlock) |
---|
1048 | 1199 | |
---|
1049 | 1200 | #include "locking-selftest-softirq.h" |
---|
1050 | | -GENERATE_PERMUTATIONS_3_EVENTS(irq_read_recursion_soft) |
---|
| 1201 | +#include "locking-selftest-rlock.h" |
---|
| 1202 | +GENERATE_PERMUTATIONS_3_EVENTS(irq_read_recursion_soft_rlock) |
---|
| 1203 | + |
---|
| 1204 | +#include "locking-selftest-wlock.h" |
---|
| 1205 | +GENERATE_PERMUTATIONS_3_EVENTS(irq_read_recursion_soft_wlock) |
---|
1051 | 1206 | |
---|
1052 | 1207 | #undef E1 |
---|
1053 | 1208 | #undef E2 |
---|
1054 | 1209 | #undef E3 |
---|
1055 | | - |
---|
1056 | | -#endif |
---|
1057 | 1210 | |
---|
1058 | 1211 | /* |
---|
1059 | 1212 | * read-lock / write-lock recursion that is unsafe. |
---|
.. | .. |
---|
1063 | 1216 | \ |
---|
1064 | 1217 | IRQ_DISABLE(); \ |
---|
1065 | 1218 | L(B); \ |
---|
1066 | | - WL(A); \ |
---|
1067 | | - WU(A); \ |
---|
| 1219 | + LOCK(A); \ |
---|
| 1220 | + UNLOCK(A); \ |
---|
1068 | 1221 | U(B); \ |
---|
1069 | 1222 | IRQ_ENABLE(); |
---|
1070 | 1223 | |
---|
.. | .. |
---|
1081 | 1234 | IRQ_EXIT(); |
---|
1082 | 1235 | |
---|
1083 | 1236 | /* |
---|
1084 | | - * Generate 12 testcases: |
---|
| 1237 | + * Generate 24 testcases: |
---|
1085 | 1238 | */ |
---|
1086 | 1239 | #include "locking-selftest-hardirq.h" |
---|
1087 | | -// GENERATE_PERMUTATIONS_3_EVENTS(irq_read_recursion2_hard) |
---|
| 1240 | +#include "locking-selftest-rlock.h" |
---|
| 1241 | +GENERATE_PERMUTATIONS_3_EVENTS(irq_read_recursion2_hard_rlock) |
---|
| 1242 | + |
---|
| 1243 | +#include "locking-selftest-wlock.h" |
---|
| 1244 | +GENERATE_PERMUTATIONS_3_EVENTS(irq_read_recursion2_hard_wlock) |
---|
1088 | 1245 | |
---|
1089 | 1246 | #include "locking-selftest-softirq.h" |
---|
1090 | | -// GENERATE_PERMUTATIONS_3_EVENTS(irq_read_recursion2_soft) |
---|
| 1247 | +#include "locking-selftest-rlock.h" |
---|
| 1248 | +GENERATE_PERMUTATIONS_3_EVENTS(irq_read_recursion2_soft_rlock) |
---|
| 1249 | + |
---|
| 1250 | +#include "locking-selftest-wlock.h" |
---|
| 1251 | +GENERATE_PERMUTATIONS_3_EVENTS(irq_read_recursion2_soft_wlock) |
---|
| 1252 | + |
---|
| 1253 | +#undef E1 |
---|
| 1254 | +#undef E2 |
---|
| 1255 | +#undef E3 |
---|
| 1256 | +/* |
---|
| 1257 | + * read-lock / write-lock recursion that is unsafe. |
---|
| 1258 | + * |
---|
| 1259 | + * A is a ENABLED_*_READ lock |
---|
| 1260 | + * B is a USED_IN_*_READ lock |
---|
| 1261 | + * |
---|
| 1262 | + * read_lock(A); |
---|
| 1263 | + * write_lock(B); |
---|
| 1264 | + * <interrupt> |
---|
| 1265 | + * read_lock(B); |
---|
| 1266 | + * write_lock(A); // if this one is read_lock(), no deadlock |
---|
| 1267 | + */ |
---|
| 1268 | + |
---|
| 1269 | +#define E1() \ |
---|
| 1270 | + \ |
---|
| 1271 | + IRQ_DISABLE(); \ |
---|
| 1272 | + WL(B); \ |
---|
| 1273 | + LOCK(A); \ |
---|
| 1274 | + UNLOCK(A); \ |
---|
| 1275 | + WU(B); \ |
---|
| 1276 | + IRQ_ENABLE(); |
---|
| 1277 | + |
---|
| 1278 | +#define E2() \ |
---|
| 1279 | + \ |
---|
| 1280 | + RL(A); \ |
---|
| 1281 | + RU(A); \ |
---|
| 1282 | + |
---|
| 1283 | +#define E3() \ |
---|
| 1284 | + \ |
---|
| 1285 | + IRQ_ENTER(); \ |
---|
| 1286 | + RL(B); \ |
---|
| 1287 | + RU(B); \ |
---|
| 1288 | + IRQ_EXIT(); |
---|
| 1289 | + |
---|
| 1290 | +/* |
---|
| 1291 | + * Generate 24 testcases: |
---|
| 1292 | + */ |
---|
| 1293 | +#include "locking-selftest-hardirq.h" |
---|
| 1294 | +#include "locking-selftest-rlock.h" |
---|
| 1295 | +GENERATE_PERMUTATIONS_3_EVENTS(irq_read_recursion3_hard_rlock) |
---|
| 1296 | + |
---|
| 1297 | +#include "locking-selftest-wlock.h" |
---|
| 1298 | +GENERATE_PERMUTATIONS_3_EVENTS(irq_read_recursion3_hard_wlock) |
---|
| 1299 | + |
---|
| 1300 | +#include "locking-selftest-softirq.h" |
---|
| 1301 | +#include "locking-selftest-rlock.h" |
---|
| 1302 | +GENERATE_PERMUTATIONS_3_EVENTS(irq_read_recursion3_soft_rlock) |
---|
| 1303 | + |
---|
| 1304 | +#include "locking-selftest-wlock.h" |
---|
| 1305 | +GENERATE_PERMUTATIONS_3_EVENTS(irq_read_recursion3_soft_wlock) |
---|
1091 | 1306 | |
---|
1092 | 1307 | #ifdef CONFIG_DEBUG_LOCK_ALLOC |
---|
1093 | 1308 | # define I_SPINLOCK(x) lockdep_reset_lock(&lock_##x.dep_map) |
---|
.. | .. |
---|
1226 | 1441 | dotest(name##_##nr, FAILURE, LOCKTYPE_RWLOCK); \ |
---|
1227 | 1442 | pr_cont("\n"); |
---|
1228 | 1443 | |
---|
| 1444 | +#define DO_TESTCASE_1RR(desc, name, nr) \ |
---|
| 1445 | + print_testname(desc"/"#nr); \ |
---|
| 1446 | + pr_cont(" |"); \ |
---|
| 1447 | + dotest(name##_##nr, SUCCESS, LOCKTYPE_RWLOCK); \ |
---|
| 1448 | + pr_cont("\n"); |
---|
| 1449 | + |
---|
| 1450 | +#define DO_TESTCASE_1RRB(desc, name, nr) \ |
---|
| 1451 | + print_testname(desc"/"#nr); \ |
---|
| 1452 | + pr_cont(" |"); \ |
---|
| 1453 | + dotest(name##_##nr, FAILURE, LOCKTYPE_RWLOCK); \ |
---|
| 1454 | + pr_cont("\n"); |
---|
| 1455 | + |
---|
| 1456 | + |
---|
1229 | 1457 | #define DO_TESTCASE_3(desc, name, nr) \ |
---|
1230 | 1458 | print_testname(desc"/"#nr); \ |
---|
1231 | 1459 | dotest(name##_spin_##nr, FAILURE, LOCKTYPE_SPIN); \ |
---|
.. | .. |
---|
1239 | 1467 | dotest(name##_wlock_##nr, FAILURE, LOCKTYPE_RWLOCK); \ |
---|
1240 | 1468 | dotest(name##_rlock_##nr, SUCCESS, LOCKTYPE_RWLOCK); \ |
---|
1241 | 1469 | pr_cont("\n"); |
---|
| 1470 | + |
---|
| 1471 | +#define DO_TESTCASE_2RW(desc, name, nr) \ |
---|
| 1472 | + print_testname(desc"/"#nr); \ |
---|
| 1473 | + pr_cont(" |"); \ |
---|
| 1474 | + dotest(name##_wlock_##nr, FAILURE, LOCKTYPE_RWLOCK); \ |
---|
| 1475 | + dotest(name##_rlock_##nr, SUCCESS, LOCKTYPE_RWLOCK); \ |
---|
| 1476 | + pr_cont("\n"); |
---|
| 1477 | + |
---|
| 1478 | +#define DO_TESTCASE_2x2RW(desc, name, nr) \ |
---|
| 1479 | + DO_TESTCASE_2RW("hard-"desc, name##_hard, nr) \ |
---|
| 1480 | + DO_TESTCASE_2RW("soft-"desc, name##_soft, nr) \ |
---|
| 1481 | + |
---|
| 1482 | +#define DO_TESTCASE_6x2x2RW(desc, name) \ |
---|
| 1483 | + DO_TESTCASE_2x2RW(desc, name, 123); \ |
---|
| 1484 | + DO_TESTCASE_2x2RW(desc, name, 132); \ |
---|
| 1485 | + DO_TESTCASE_2x2RW(desc, name, 213); \ |
---|
| 1486 | + DO_TESTCASE_2x2RW(desc, name, 231); \ |
---|
| 1487 | + DO_TESTCASE_2x2RW(desc, name, 312); \ |
---|
| 1488 | + DO_TESTCASE_2x2RW(desc, name, 321); |
---|
1242 | 1489 | |
---|
1243 | 1490 | #define DO_TESTCASE_6(desc, name) \ |
---|
1244 | 1491 | print_testname(desc); \ |
---|
.. | .. |
---|
1315 | 1562 | DO_TESTCASE_2IB(desc, name, 231); \ |
---|
1316 | 1563 | DO_TESTCASE_2IB(desc, name, 312); \ |
---|
1317 | 1564 | DO_TESTCASE_2IB(desc, name, 321); |
---|
| 1565 | + |
---|
| 1566 | +#define DO_TESTCASE_6x1RR(desc, name) \ |
---|
| 1567 | + DO_TESTCASE_1RR(desc, name, 123); \ |
---|
| 1568 | + DO_TESTCASE_1RR(desc, name, 132); \ |
---|
| 1569 | + DO_TESTCASE_1RR(desc, name, 213); \ |
---|
| 1570 | + DO_TESTCASE_1RR(desc, name, 231); \ |
---|
| 1571 | + DO_TESTCASE_1RR(desc, name, 312); \ |
---|
| 1572 | + DO_TESTCASE_1RR(desc, name, 321); |
---|
| 1573 | + |
---|
| 1574 | +#define DO_TESTCASE_6x1RRB(desc, name) \ |
---|
| 1575 | + DO_TESTCASE_1RRB(desc, name, 123); \ |
---|
| 1576 | + DO_TESTCASE_1RRB(desc, name, 132); \ |
---|
| 1577 | + DO_TESTCASE_1RRB(desc, name, 213); \ |
---|
| 1578 | + DO_TESTCASE_1RRB(desc, name, 231); \ |
---|
| 1579 | + DO_TESTCASE_1RRB(desc, name, 312); \ |
---|
| 1580 | + DO_TESTCASE_1RRB(desc, name, 321); |
---|
1318 | 1581 | |
---|
1319 | 1582 | #define DO_TESTCASE_6x6(desc, name) \ |
---|
1320 | 1583 | DO_TESTCASE_6I(desc, name, 123); \ |
---|
.. | .. |
---|
1502 | 1765 | |
---|
1503 | 1766 | mutex_lock(&o2.base); |
---|
1504 | 1767 | o2.ctx = &t2; |
---|
1505 | | - mutex_release(&o2.base.dep_map, 1, _THIS_IP_); |
---|
| 1768 | + mutex_release(&o2.base.dep_map, _THIS_IP_); |
---|
1506 | 1769 | |
---|
1507 | 1770 | WWAI(&t); |
---|
1508 | 1771 | t2 = t; |
---|
.. | .. |
---|
1527 | 1790 | int ret; |
---|
1528 | 1791 | |
---|
1529 | 1792 | mutex_lock(&o2.base); |
---|
1530 | | - mutex_release(&o2.base.dep_map, 1, _THIS_IP_); |
---|
| 1793 | + mutex_release(&o2.base.dep_map, _THIS_IP_); |
---|
1531 | 1794 | o2.ctx = &t2; |
---|
1532 | 1795 | |
---|
1533 | 1796 | WWAI(&t); |
---|
.. | .. |
---|
1554 | 1817 | |
---|
1555 | 1818 | mutex_lock(&o2.base); |
---|
1556 | 1819 | o2.ctx = &t2; |
---|
1557 | | - mutex_release(&o2.base.dep_map, 1, _THIS_IP_); |
---|
| 1820 | + mutex_release(&o2.base.dep_map, _THIS_IP_); |
---|
1558 | 1821 | |
---|
1559 | 1822 | WWAI(&t); |
---|
1560 | 1823 | t2 = t; |
---|
.. | .. |
---|
1578 | 1841 | int ret; |
---|
1579 | 1842 | |
---|
1580 | 1843 | mutex_lock(&o2.base); |
---|
1581 | | - mutex_release(&o2.base.dep_map, 1, _THIS_IP_); |
---|
| 1844 | + mutex_release(&o2.base.dep_map, _THIS_IP_); |
---|
1582 | 1845 | o2.ctx = &t2; |
---|
1583 | 1846 | |
---|
1584 | 1847 | WWAI(&t); |
---|
.. | .. |
---|
1603 | 1866 | int ret; |
---|
1604 | 1867 | |
---|
1605 | 1868 | mutex_lock(&o2.base); |
---|
1606 | | - mutex_release(&o2.base.dep_map, 1, _THIS_IP_); |
---|
| 1869 | + mutex_release(&o2.base.dep_map, _THIS_IP_); |
---|
1607 | 1870 | o2.ctx = &t2; |
---|
1608 | 1871 | |
---|
1609 | 1872 | WWAI(&t); |
---|
.. | .. |
---|
1624 | 1887 | int ret; |
---|
1625 | 1888 | |
---|
1626 | 1889 | mutex_lock(&o2.base); |
---|
1627 | | - mutex_release(&o2.base.dep_map, 1, _THIS_IP_); |
---|
| 1890 | + mutex_release(&o2.base.dep_map, _THIS_IP_); |
---|
1628 | 1891 | o2.ctx = &t2; |
---|
1629 | 1892 | |
---|
1630 | 1893 | WWAI(&t); |
---|
.. | .. |
---|
1645 | 1908 | int ret; |
---|
1646 | 1909 | |
---|
1647 | 1910 | mutex_lock(&o2.base); |
---|
1648 | | - mutex_release(&o2.base.dep_map, 1, _THIS_IP_); |
---|
| 1911 | + mutex_release(&o2.base.dep_map, _THIS_IP_); |
---|
1649 | 1912 | o2.ctx = &t2; |
---|
1650 | 1913 | |
---|
1651 | 1914 | mutex_lock(&o3.base); |
---|
1652 | | - mutex_release(&o3.base.dep_map, 1, _THIS_IP_); |
---|
| 1915 | + mutex_release(&o3.base.dep_map, _THIS_IP_); |
---|
1653 | 1916 | o3.ctx = &t2; |
---|
1654 | 1917 | |
---|
1655 | 1918 | WWAI(&t); |
---|
.. | .. |
---|
1671 | 1934 | int ret; |
---|
1672 | 1935 | |
---|
1673 | 1936 | mutex_lock(&o2.base); |
---|
1674 | | - mutex_release(&o2.base.dep_map, 1, _THIS_IP_); |
---|
| 1937 | + mutex_release(&o2.base.dep_map, _THIS_IP_); |
---|
1675 | 1938 | o2.ctx = &t2; |
---|
1676 | 1939 | |
---|
1677 | 1940 | mutex_lock(&o3.base); |
---|
1678 | | - mutex_release(&o3.base.dep_map, 1, _THIS_IP_); |
---|
| 1941 | + mutex_release(&o3.base.dep_map, _THIS_IP_); |
---|
1679 | 1942 | o3.ctx = &t2; |
---|
1680 | 1943 | |
---|
1681 | 1944 | WWAI(&t); |
---|
.. | .. |
---|
1696 | 1959 | int ret; |
---|
1697 | 1960 | |
---|
1698 | 1961 | mutex_lock(&o2.base); |
---|
1699 | | - mutex_release(&o2.base.dep_map, 1, _THIS_IP_); |
---|
| 1962 | + mutex_release(&o2.base.dep_map, _THIS_IP_); |
---|
1700 | 1963 | o2.ctx = &t2; |
---|
1701 | 1964 | |
---|
1702 | 1965 | WWAI(&t); |
---|
.. | .. |
---|
1721 | 1984 | int ret; |
---|
1722 | 1985 | |
---|
1723 | 1986 | mutex_lock(&o2.base); |
---|
1724 | | - mutex_release(&o2.base.dep_map, 1, _THIS_IP_); |
---|
| 1987 | + mutex_release(&o2.base.dep_map, _THIS_IP_); |
---|
1725 | 1988 | o2.ctx = &t2; |
---|
1726 | 1989 | |
---|
1727 | 1990 | WWAI(&t); |
---|
.. | .. |
---|
1993 | 2256 | pr_cont("\n"); |
---|
1994 | 2257 | } |
---|
1995 | 2258 | |
---|
| 2259 | + |
---|
| 2260 | +/* |
---|
| 2261 | + * <in hardirq handler> |
---|
| 2262 | + * read_lock(&A); |
---|
| 2263 | + * <hardirq disable> |
---|
| 2264 | + * spin_lock(&B); |
---|
| 2265 | + * spin_lock(&B); |
---|
| 2266 | + * read_lock(&A); |
---|
| 2267 | + * |
---|
| 2268 | + * is a deadlock. |
---|
| 2269 | + */ |
---|
| 2270 | +static void queued_read_lock_hardirq_RE_Er(void) |
---|
| 2271 | +{ |
---|
| 2272 | + HARDIRQ_ENTER(); |
---|
| 2273 | + read_lock(&rwlock_A); |
---|
| 2274 | + LOCK(B); |
---|
| 2275 | + UNLOCK(B); |
---|
| 2276 | + read_unlock(&rwlock_A); |
---|
| 2277 | + HARDIRQ_EXIT(); |
---|
| 2278 | + |
---|
| 2279 | + HARDIRQ_DISABLE(); |
---|
| 2280 | + LOCK(B); |
---|
| 2281 | + read_lock(&rwlock_A); |
---|
| 2282 | + read_unlock(&rwlock_A); |
---|
| 2283 | + UNLOCK(B); |
---|
| 2284 | + HARDIRQ_ENABLE(); |
---|
| 2285 | +} |
---|
| 2286 | + |
---|
| 2287 | +/* |
---|
| 2288 | + * <in hardirq handler> |
---|
| 2289 | + * spin_lock(&B); |
---|
| 2290 | + * <hardirq disable> |
---|
| 2291 | + * read_lock(&A); |
---|
| 2292 | + * read_lock(&A); |
---|
| 2293 | + * spin_lock(&B); |
---|
| 2294 | + * |
---|
| 2295 | + * is not a deadlock. |
---|
| 2296 | + */ |
---|
| 2297 | +static void queued_read_lock_hardirq_ER_rE(void) |
---|
| 2298 | +{ |
---|
| 2299 | + HARDIRQ_ENTER(); |
---|
| 2300 | + LOCK(B); |
---|
| 2301 | + read_lock(&rwlock_A); |
---|
| 2302 | + read_unlock(&rwlock_A); |
---|
| 2303 | + UNLOCK(B); |
---|
| 2304 | + HARDIRQ_EXIT(); |
---|
| 2305 | + |
---|
| 2306 | + HARDIRQ_DISABLE(); |
---|
| 2307 | + read_lock(&rwlock_A); |
---|
| 2308 | + LOCK(B); |
---|
| 2309 | + UNLOCK(B); |
---|
| 2310 | + read_unlock(&rwlock_A); |
---|
| 2311 | + HARDIRQ_ENABLE(); |
---|
| 2312 | +} |
---|
| 2313 | + |
---|
| 2314 | +/* |
---|
| 2315 | + * <hardirq disable> |
---|
| 2316 | + * spin_lock(&B); |
---|
| 2317 | + * read_lock(&A); |
---|
| 2318 | + * <in hardirq handler> |
---|
| 2319 | + * spin_lock(&B); |
---|
| 2320 | + * read_lock(&A); |
---|
| 2321 | + * |
---|
| 2322 | + * is a deadlock. Because the two read_lock()s are both non-recursive readers. |
---|
| 2323 | + */ |
---|
| 2324 | +static void queued_read_lock_hardirq_inversion(void) |
---|
| 2325 | +{ |
---|
| 2326 | + |
---|
| 2327 | + HARDIRQ_ENTER(); |
---|
| 2328 | + LOCK(B); |
---|
| 2329 | + UNLOCK(B); |
---|
| 2330 | + HARDIRQ_EXIT(); |
---|
| 2331 | + |
---|
| 2332 | + HARDIRQ_DISABLE(); |
---|
| 2333 | + LOCK(B); |
---|
| 2334 | + read_lock(&rwlock_A); |
---|
| 2335 | + read_unlock(&rwlock_A); |
---|
| 2336 | + UNLOCK(B); |
---|
| 2337 | + HARDIRQ_ENABLE(); |
---|
| 2338 | + |
---|
| 2339 | + read_lock(&rwlock_A); |
---|
| 2340 | + read_unlock(&rwlock_A); |
---|
| 2341 | +} |
---|
| 2342 | + |
---|
| 2343 | +static void queued_read_lock_tests(void) |
---|
| 2344 | +{ |
---|
| 2345 | + printk(" --------------------------------------------------------------------------\n"); |
---|
| 2346 | + printk(" | queued read lock tests |\n"); |
---|
| 2347 | + printk(" ---------------------------\n"); |
---|
| 2348 | + print_testname("hardirq read-lock/lock-read"); |
---|
| 2349 | + dotest(queued_read_lock_hardirq_RE_Er, FAILURE, LOCKTYPE_RWLOCK); |
---|
| 2350 | + pr_cont("\n"); |
---|
| 2351 | + |
---|
| 2352 | + print_testname("hardirq lock-read/read-lock"); |
---|
| 2353 | + dotest(queued_read_lock_hardirq_ER_rE, SUCCESS, LOCKTYPE_RWLOCK); |
---|
| 2354 | + pr_cont("\n"); |
---|
| 2355 | + |
---|
| 2356 | + print_testname("hardirq inversion"); |
---|
| 2357 | + dotest(queued_read_lock_hardirq_inversion, FAILURE, LOCKTYPE_RWLOCK); |
---|
| 2358 | + pr_cont("\n"); |
---|
| 2359 | +} |
---|
| 2360 | + |
---|
1996 | 2361 | void locking_selftest(void) |
---|
1997 | 2362 | { |
---|
1998 | 2363 | /* |
---|
.. | .. |
---|
2006 | 2371 | } |
---|
2007 | 2372 | |
---|
2008 | 2373 | /* |
---|
| 2374 | + * treats read_lock() as recursive read locks for testing purpose |
---|
| 2375 | + */ |
---|
| 2376 | + force_read_lock_recursive = 1; |
---|
| 2377 | + |
---|
| 2378 | + /* |
---|
2009 | 2379 | * Run the testsuite: |
---|
2010 | 2380 | */ |
---|
2011 | 2381 | printk("------------------------\n"); |
---|
.. | .. |
---|
2016 | 2386 | |
---|
2017 | 2387 | init_shared_classes(); |
---|
2018 | 2388 | debug_locks_silent = !debug_locks_verbose; |
---|
| 2389 | + lockdep_set_selftest_task(current); |
---|
2019 | 2390 | |
---|
2020 | 2391 | DO_TESTCASE_6R("A-A deadlock", AA); |
---|
2021 | 2392 | DO_TESTCASE_6R("A-B-B-A deadlock", ABBA); |
---|
.. | .. |
---|
2059 | 2430 | print_testname("mixed read-lock/lock-write ABBA"); |
---|
2060 | 2431 | pr_cont(" |"); |
---|
2061 | 2432 | dotest(rlock_ABBA1, FAILURE, LOCKTYPE_RWLOCK); |
---|
2062 | | -#ifdef CONFIG_PROVE_LOCKING |
---|
2063 | | - /* |
---|
2064 | | - * Lockdep does indeed fail here, but there's nothing we can do about |
---|
2065 | | - * that now. Don't kill lockdep for it. |
---|
2066 | | - */ |
---|
2067 | | - unexpected_testcase_failures--; |
---|
2068 | | -#endif |
---|
2069 | | - |
---|
2070 | 2433 | pr_cont(" |"); |
---|
2071 | 2434 | dotest(rwsem_ABBA1, FAILURE, LOCKTYPE_RWSEM); |
---|
2072 | 2435 | |
---|
.. | .. |
---|
2082 | 2445 | pr_cont(" |"); |
---|
2083 | 2446 | dotest(rwsem_ABBA3, FAILURE, LOCKTYPE_RWSEM); |
---|
2084 | 2447 | |
---|
| 2448 | + print_testname("chain cached mixed R-L/L-W ABBA"); |
---|
| 2449 | + pr_cont(" |"); |
---|
| 2450 | + dotest(rlock_chaincache_ABBA1, FAILURE, LOCKTYPE_RWLOCK); |
---|
| 2451 | + |
---|
| 2452 | + DO_TESTCASE_6x1RRB("rlock W1R2/W2R3/W3R1", W1R2_W2R3_W3R1); |
---|
| 2453 | + DO_TESTCASE_6x1RRB("rlock W1W2/R2R3/W3R1", W1W2_R2R3_W3R1); |
---|
| 2454 | + DO_TESTCASE_6x1RR("rlock W1W2/R2R3/R3W1", W1W2_R2R3_R3W1); |
---|
| 2455 | + DO_TESTCASE_6x1RR("rlock W1R2/R2R3/W3W1", W1R2_R2R3_W3W1); |
---|
| 2456 | + |
---|
2085 | 2457 | printk(" --------------------------------------------------------------------------\n"); |
---|
2086 | 2458 | |
---|
2087 | | -#ifndef CONFIG_PREEMPT_RT_FULL |
---|
2088 | 2459 | /* |
---|
2089 | 2460 | * irq-context testcases: |
---|
2090 | 2461 | */ |
---|
.. | .. |
---|
2095 | 2466 | DO_TESTCASE_6x6("safe-A + unsafe-B #2", irqsafe4); |
---|
2096 | 2467 | DO_TESTCASE_6x6RW("irq lock-inversion", irq_inversion); |
---|
2097 | 2468 | |
---|
2098 | | - DO_TESTCASE_6x2("irq read-recursion", irq_read_recursion); |
---|
2099 | | -// DO_TESTCASE_6x2B("irq read-recursion #2", irq_read_recursion2); |
---|
2100 | | -#else |
---|
2101 | | - /* On -rt, we only do hardirq context test for raw spinlock */ |
---|
2102 | | - DO_TESTCASE_1B("hard-irqs-on + irq-safe-A", irqsafe1_hard_spin, 12); |
---|
2103 | | - DO_TESTCASE_1B("hard-irqs-on + irq-safe-A", irqsafe1_hard_spin, 21); |
---|
2104 | | - |
---|
2105 | | - DO_TESTCASE_1B("hard-safe-A + irqs-on", irqsafe2B_hard_spin, 12); |
---|
2106 | | - DO_TESTCASE_1B("hard-safe-A + irqs-on", irqsafe2B_hard_spin, 21); |
---|
2107 | | - |
---|
2108 | | - DO_TESTCASE_1B("hard-safe-A + unsafe-B #1", irqsafe3_hard_spin, 123); |
---|
2109 | | - DO_TESTCASE_1B("hard-safe-A + unsafe-B #1", irqsafe3_hard_spin, 132); |
---|
2110 | | - DO_TESTCASE_1B("hard-safe-A + unsafe-B #1", irqsafe3_hard_spin, 213); |
---|
2111 | | - DO_TESTCASE_1B("hard-safe-A + unsafe-B #1", irqsafe3_hard_spin, 231); |
---|
2112 | | - DO_TESTCASE_1B("hard-safe-A + unsafe-B #1", irqsafe3_hard_spin, 312); |
---|
2113 | | - DO_TESTCASE_1B("hard-safe-A + unsafe-B #1", irqsafe3_hard_spin, 321); |
---|
2114 | | - |
---|
2115 | | - DO_TESTCASE_1B("hard-safe-A + unsafe-B #2", irqsafe4_hard_spin, 123); |
---|
2116 | | - DO_TESTCASE_1B("hard-safe-A + unsafe-B #2", irqsafe4_hard_spin, 132); |
---|
2117 | | - DO_TESTCASE_1B("hard-safe-A + unsafe-B #2", irqsafe4_hard_spin, 213); |
---|
2118 | | - DO_TESTCASE_1B("hard-safe-A + unsafe-B #2", irqsafe4_hard_spin, 231); |
---|
2119 | | - DO_TESTCASE_1B("hard-safe-A + unsafe-B #2", irqsafe4_hard_spin, 312); |
---|
2120 | | - DO_TESTCASE_1B("hard-safe-A + unsafe-B #2", irqsafe4_hard_spin, 321); |
---|
2121 | | -#endif |
---|
| 2469 | + DO_TESTCASE_6x2x2RW("irq read-recursion", irq_read_recursion); |
---|
| 2470 | + DO_TESTCASE_6x2x2RW("irq read-recursion #2", irq_read_recursion2); |
---|
| 2471 | + DO_TESTCASE_6x2x2RW("irq read-recursion #3", irq_read_recursion3); |
---|
2122 | 2472 | |
---|
2123 | 2473 | ww_tests(); |
---|
| 2474 | + |
---|
| 2475 | + force_read_lock_recursive = 0; |
---|
| 2476 | + /* |
---|
| 2477 | + * queued_read_lock() specific test cases can be put here |
---|
| 2478 | + */ |
---|
| 2479 | + if (IS_ENABLED(CONFIG_QUEUED_RWLOCKS)) |
---|
| 2480 | + queued_read_lock_tests(); |
---|
2124 | 2481 | |
---|
2125 | 2482 | if (unexpected_testcase_failures) { |
---|
2126 | 2483 | printk("-----------------------------------------------------------------\n"); |
---|
.. | .. |
---|
2147 | 2504 | printk("---------------------------------\n"); |
---|
2148 | 2505 | debug_locks = 1; |
---|
2149 | 2506 | } |
---|
| 2507 | + lockdep_set_selftest_task(NULL); |
---|
2150 | 2508 | debug_locks_silent = 0; |
---|
2151 | 2509 | } |
---|