#include struct set { queue_t s_list; char s_name[OBJECT_NAME_MAX]; spin_lock_t s_lock; }; static object_type_t set_type = { .ob_name = "set", .ob_size = sizeof(struct set), }; void init_set_objects(void) { object_type_register(&set_type); } object_t *set_create(const char *name) { object_t *set_obj = object_create(&set_type); if (!set_obj) { return NULL; } struct set *set = object_data(set_obj); set->s_list = QUEUE_INIT; set->s_lock = SPIN_LOCK_INIT; strncpy(set->s_name, name, sizeof set->s_name - 1); set->s_name[sizeof set->s_name - 1] = 0; return set_obj; } kern_status_t set_lock(object_t *obj, unsigned long *flags) { if (!object_is_set(obj)) { return KERN_INVALID_ARGUMENT; } struct set *set = object_data(obj); spin_lock_irqsave(&set->s_lock, flags); return KERN_OK; } kern_status_t set_unlock(object_t *obj, unsigned long flags) { if (!object_is_set(obj)) { return KERN_INVALID_ARGUMENT; } struct set *set = object_data(obj); spin_unlock_irqrestore(&set->s_lock, flags); return KERN_OK; } kern_status_t set_add_object(object_t *set_obj, object_t *obj) { if (!object_is_set(set_obj)) { return KERN_INVALID_ARGUMENT; } struct set *set = object_data(set_obj); char child_name[OBJECT_NAME_MAX]; char obj_name[OBJECT_NAME_MAX]; kern_status_t status = object_query_name(obj, obj_name); if (status != KERN_OK) { return status; } queue_foreach (object_t, child, &set->s_list, ob_list) { object_query_name(child, child_name); if (!strcmp(child_name, obj_name)) { return KERN_NAME_EXISTS; } } queue_push_back(&set->s_list, &obj->ob_list); return KERN_OK; } kern_status_t set_remove_object(object_t *set_obj, object_t *obj) { if (!object_is_set(set_obj)) { return KERN_INVALID_ARGUMENT; } struct set *set = object_data(set_obj); queue_delete(&set->s_list, &obj->ob_list); return KERN_OK; } bool object_is_set(object_t *obj) { return obj->ob_type == &set_type; }