|
@@ -95,7 +95,9 @@ struct efi_device * efidev_parent ( struct device *dev ) {
|
95
|
95
|
static EFI_STATUS EFIAPI
|
96
|
96
|
efi_driver_supported ( EFI_DRIVER_BINDING_PROTOCOL *driver __unused,
|
97
|
97
|
EFI_HANDLE device, EFI_DEVICE_PATH_PROTOCOL *child ) {
|
|
98
|
+ EFI_BOOT_SERVICES *bs = efi_systab->BootServices;
|
98
|
99
|
struct efi_driver *efidrv;
|
|
100
|
+ EFI_TPL saved_tpl;
|
99
|
101
|
int rc;
|
100
|
102
|
|
101
|
103
|
DBGCP ( device, "EFIDRV %s DRIVER_SUPPORTED",
|
|
@@ -111,17 +113,22 @@ efi_driver_supported ( EFI_DRIVER_BINDING_PROTOCOL *driver __unused,
|
111
|
113
|
return EFI_ALREADY_STARTED;
|
112
|
114
|
}
|
113
|
115
|
|
|
116
|
+ /* Raise TPL */
|
|
117
|
+ saved_tpl = bs->RaiseTPL ( TPL_CALLBACK );
|
|
118
|
+
|
114
|
119
|
/* Look for a driver claiming to support this device */
|
115
|
120
|
for_each_table_entry ( efidrv, EFI_DRIVERS ) {
|
116
|
121
|
if ( ( rc = efidrv->supported ( device ) ) == 0 ) {
|
117
|
122
|
DBGC ( device, "EFIDRV %s has driver \"%s\"\n",
|
118
|
123
|
efi_handle_name ( device ), efidrv->name );
|
|
124
|
+ bs->RestoreTPL ( saved_tpl );
|
119
|
125
|
return 0;
|
120
|
126
|
}
|
121
|
127
|
}
|
122
|
128
|
DBGCP ( device, "EFIDRV %s has no driver\n",
|
123
|
129
|
efi_handle_name ( device ) );
|
124
|
130
|
|
|
131
|
+ bs->RestoreTPL ( saved_tpl );
|
125
|
132
|
return EFI_UNSUPPORTED;
|
126
|
133
|
}
|
127
|
134
|
|
|
@@ -145,6 +152,7 @@ efi_driver_start ( EFI_DRIVER_BINDING_PROTOCOL *driver __unused,
|
145
|
152
|
} path;
|
146
|
153
|
EFI_DEVICE_PATH_PROTOCOL *path_end;
|
147
|
154
|
size_t path_len;
|
|
155
|
+ EFI_TPL saved_tpl;
|
148
|
156
|
EFI_STATUS efirc;
|
149
|
157
|
int rc;
|
150
|
158
|
|
|
@@ -162,6 +170,9 @@ efi_driver_start ( EFI_DRIVER_BINDING_PROTOCOL *driver __unused,
|
162
|
170
|
goto err_already_started;
|
163
|
171
|
}
|
164
|
172
|
|
|
173
|
+ /* Raise TPL */
|
|
174
|
+ saved_tpl = bs->RaiseTPL ( TPL_CALLBACK );
|
|
175
|
+
|
165
|
176
|
/* Do nothing if we are currently disconnecting drivers */
|
166
|
177
|
if ( efi_driver_disconnecting ) {
|
167
|
178
|
DBGC ( device, "EFIDRV %s refusing to start during "
|
|
@@ -215,6 +226,7 @@ efi_driver_start ( EFI_DRIVER_BINDING_PROTOCOL *driver __unused,
|
215
|
226
|
DBGC ( device, "EFIDRV %s using driver \"%s\"\n",
|
216
|
227
|
efi_handle_name ( device ),
|
217
|
228
|
efidev->driver->name );
|
|
229
|
+ bs->RestoreTPL ( saved_tpl );
|
218
|
230
|
return 0;
|
219
|
231
|
}
|
220
|
232
|
DBGC ( device, "EFIDRV %s could not start driver \"%s\": %s\n",
|
|
@@ -232,6 +244,7 @@ efi_driver_start ( EFI_DRIVER_BINDING_PROTOCOL *driver __unused,
|
232
|
244
|
}
|
233
|
245
|
err_open_path:
|
234
|
246
|
err_disconnecting:
|
|
247
|
+ bs->RestoreTPL ( saved_tpl );
|
235
|
248
|
err_already_started:
|
236
|
249
|
return efirc;
|
237
|
250
|
}
|
|
@@ -250,8 +263,10 @@ static EFI_STATUS EFIAPI
|
250
|
263
|
efi_driver_stop ( EFI_DRIVER_BINDING_PROTOCOL *driver __unused,
|
251
|
264
|
EFI_HANDLE device, UINTN num_children,
|
252
|
265
|
EFI_HANDLE *children ) {
|
|
266
|
+ EFI_BOOT_SERVICES *bs = efi_systab->BootServices;
|
253
|
267
|
struct efi_driver *efidrv;
|
254
|
268
|
struct efi_device *efidev;
|
|
269
|
+ EFI_TPL saved_tpl;
|
255
|
270
|
UINTN i;
|
256
|
271
|
|
257
|
272
|
DBGC ( device, "EFIDRV %s DRIVER_STOP", efi_handle_name ( device ) );
|
|
@@ -269,6 +284,9 @@ efi_driver_stop ( EFI_DRIVER_BINDING_PROTOCOL *driver __unused,
|
269
|
284
|
return EFI_DEVICE_ERROR;
|
270
|
285
|
}
|
271
|
286
|
|
|
287
|
+ /* Raise TPL */
|
|
288
|
+ saved_tpl = bs->RaiseTPL ( TPL_CALLBACK );
|
|
289
|
+
|
272
|
290
|
/* Stop this device */
|
273
|
291
|
efidrv = efidev->driver;
|
274
|
292
|
assert ( efidrv != NULL );
|
|
@@ -276,6 +294,7 @@ efi_driver_stop ( EFI_DRIVER_BINDING_PROTOCOL *driver __unused,
|
276
|
294
|
list_del ( &efidev->dev.siblings );
|
277
|
295
|
free ( efidev );
|
278
|
296
|
|
|
297
|
+ bs->RestoreTPL ( saved_tpl );
|
279
|
298
|
return 0;
|
280
|
299
|
}
|
281
|
300
|
|