Fix driver_settings in kernel mode outside of drivers.
The API allows to create driver settings which are not added to the global list, however those were left partially uninitialized, and there was no way to cleanly delete them. Tag such unattached settings with a ref_count of -1, and have delete_driver_settings check for this and handle the case correctly. Note: #10494 comment 2 says the settings for packagefs shouldn't be added to the kernel driver settings list, which is why I went with this solution. An alternative would be always using the list and the reference counting, but I don't know what the consequences are. Fixes #10494.
This commit is contained in:
parent
0687a01b53
commit
bcb793d37b
@ -77,6 +77,8 @@ typedef struct settings_handle {
|
||||
list_link link;
|
||||
char name[B_OS_NAME_LENGTH];
|
||||
int32 ref_count;
|
||||
// A negative ref_count means the node is not reference counted and not
|
||||
// stored in the list.
|
||||
#endif
|
||||
int32 magic;
|
||||
struct driver_settings settings;
|
||||
@ -101,8 +103,9 @@ static mutex sLock = MUTEX_INITIALIZER("driver settings");
|
||||
|
||||
|
||||
/*!
|
||||
Returns true for any characters that separate parameters -
|
||||
those are ignored in the input stream and won't be added
|
||||
\brief Returns true for any characters that separate parameters
|
||||
|
||||
Those characters are ignored in the input stream and won't be added
|
||||
to any words.
|
||||
*/
|
||||
static inline bool
|
||||
@ -112,9 +115,8 @@ is_parameter_separator(char c)
|
||||
}
|
||||
|
||||
|
||||
/** Indicates if "c" begins a new word or not.
|
||||
*/
|
||||
|
||||
/*! Indicates if "c" begins a new word or not.
|
||||
*/
|
||||
static inline bool
|
||||
is_word_break(char c)
|
||||
{
|
||||
@ -413,6 +415,9 @@ new_settings(char *buffer, const char *driverName)
|
||||
if (driverName != NULL) {
|
||||
handle->ref_count = 1;
|
||||
strlcpy(handle->name, driverName, sizeof(handle->name));
|
||||
} else {
|
||||
handle->ref_count = -1;
|
||||
handle->name[0] = 0;
|
||||
}
|
||||
#endif
|
||||
|
||||
@ -687,11 +692,14 @@ unload_driver_settings(void *_handle)
|
||||
|
||||
#ifdef _KERNEL_MODE
|
||||
mutex_lock(&sLock);
|
||||
if (--handle->ref_count == 0 && gBootDevice > 0) {
|
||||
// don't unload an handle when /boot is not available
|
||||
list_remove_link(&handle->link);
|
||||
} else
|
||||
handle = NULL;
|
||||
|
||||
if (handle->ref_count > 0) {
|
||||
if (--handle->ref_count == 0 && gBootDevice > 0) {
|
||||
// don't unload an handle when /boot is not available
|
||||
list_remove_link(&handle->link);
|
||||
} else
|
||||
handle = NULL;
|
||||
}
|
||||
mutex_unlock(&sLock);
|
||||
#endif
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user