41
41
#include <linux/tracehook.h>
42
42
#include <linux/uaccess.h>
43
43
#include <linux/anon_inodes.h>
44
+ #include <linux/lockdep.h>
44
45
45
46
enum notify_state {
46
47
SECCOMP_NOTIFY_INIT ,
@@ -1024,6 +1025,23 @@ static int seccomp_notify_release(struct inode *inode, struct file *file)
1024
1025
return 0 ;
1025
1026
}
1026
1027
1028
+ /* must be called with notif_lock held */
1029
+ static inline struct seccomp_knotif *
1030
+ find_notification (struct seccomp_filter * filter , u64 id )
1031
+ {
1032
+ struct seccomp_knotif * cur ;
1033
+
1034
+ lockdep_assert_held (& filter -> notify_lock );
1035
+
1036
+ list_for_each_entry (cur , & filter -> notif -> notifications , list ) {
1037
+ if (cur -> id == id )
1038
+ return cur ;
1039
+ }
1040
+
1041
+ return NULL ;
1042
+ }
1043
+
1044
+
1027
1045
static long seccomp_notify_recv (struct seccomp_filter * filter ,
1028
1046
void __user * buf )
1029
1047
{
@@ -1081,15 +1099,8 @@ static long seccomp_notify_recv(struct seccomp_filter *filter,
1081
1099
* may have died when we released the lock, so we need to make
1082
1100
* sure it's still around.
1083
1101
*/
1084
- knotif = NULL ;
1085
1102
mutex_lock (& filter -> notify_lock );
1086
- list_for_each_entry (cur , & filter -> notif -> notifications , list ) {
1087
- if (cur -> id == unotif .id ) {
1088
- knotif = cur ;
1089
- break ;
1090
- }
1091
- }
1092
-
1103
+ knotif = find_notification (filter , unotif .id );
1093
1104
if (knotif ) {
1094
1105
knotif -> state = SECCOMP_NOTIFY_INIT ;
1095
1106
up (& filter -> notif -> request );
@@ -1104,7 +1115,7 @@ static long seccomp_notify_send(struct seccomp_filter *filter,
1104
1115
void __user * buf )
1105
1116
{
1106
1117
struct seccomp_notif_resp resp = {};
1107
- struct seccomp_knotif * knotif = NULL , * cur ;
1118
+ struct seccomp_knotif * knotif ;
1108
1119
long ret ;
1109
1120
1110
1121
if (copy_from_user (& resp , buf , sizeof (resp )))
@@ -1121,13 +1132,7 @@ static long seccomp_notify_send(struct seccomp_filter *filter,
1121
1132
if (ret < 0 )
1122
1133
return ret ;
1123
1134
1124
- list_for_each_entry (cur , & filter -> notif -> notifications , list ) {
1125
- if (cur -> id == resp .id ) {
1126
- knotif = cur ;
1127
- break ;
1128
- }
1129
- }
1130
-
1135
+ knotif = find_notification (filter , resp .id );
1131
1136
if (!knotif ) {
1132
1137
ret = - ENOENT ;
1133
1138
goto out ;
@@ -1153,7 +1158,7 @@ static long seccomp_notify_send(struct seccomp_filter *filter,
1153
1158
static long seccomp_notify_id_valid (struct seccomp_filter * filter ,
1154
1159
void __user * buf )
1155
1160
{
1156
- struct seccomp_knotif * knotif = NULL ;
1161
+ struct seccomp_knotif * knotif ;
1157
1162
u64 id ;
1158
1163
long ret ;
1159
1164
@@ -1164,16 +1169,12 @@ static long seccomp_notify_id_valid(struct seccomp_filter *filter,
1164
1169
if (ret < 0 )
1165
1170
return ret ;
1166
1171
1167
- ret = - ENOENT ;
1168
- list_for_each_entry (knotif , & filter -> notif -> notifications , list ) {
1169
- if (knotif -> id == id ) {
1170
- if (knotif -> state == SECCOMP_NOTIFY_SENT )
1171
- ret = 0 ;
1172
- goto out ;
1173
- }
1174
- }
1172
+ knotif = find_notification (filter , id );
1173
+ if (knotif && knotif -> state == SECCOMP_NOTIFY_SENT )
1174
+ ret = 0 ;
1175
+ else
1176
+ ret = - ENOENT ;
1175
1177
1176
- out :
1177
1178
mutex_unlock (& filter -> notify_lock );
1178
1179
return ret ;
1179
1180
}
0 commit comments