diff options
-rw-r--r-- | libhurd-cap-server/ChangeLog | 18 | ||||
-rw-r--r-- | libhurd-cap-server/cap-server.h | 56 | ||||
-rw-r--r-- | libhurd-cap-server/class-create.c | 7 | ||||
-rw-r--r-- | libhurd-cap-server/class-init.c | 19 | ||||
-rw-r--r-- | libhurd-cap-server/obj-copy-out.c | 2 |
5 files changed, 64 insertions, 38 deletions
diff --git a/libhurd-cap-server/ChangeLog b/libhurd-cap-server/ChangeLog index 62d7801..d0a951d 100644 --- a/libhurd-cap-server/ChangeLog +++ b/libhurd-cap-server/ChangeLog @@ -1,5 +1,23 @@ 2004-11-30 Neal H. Walfield <neal@gnu.org> + * cap-server.h: Improve comments. + (hurd_cap_class_create_untyped): Tighten alignment restrictions: + ALIGNMENT must be a power of 2. + * class-init.c (hurd_cap_class_init_untyped): Calculate best + alignment. + + * cap-server.h (hurd_cap_obj_get_size): Renamed to ... + (hurd_cap_obj_user_offset): ... this. + (hurd_cap_obj_to_user_untyped): Call hurd_cap_obj_user_offset, not + hurd_cap_obj_get_size. + (hurd_cap_obj_from_user_untyped): Likewise. + * class-init.c (hurd_cap_class_init_untyped): Likewise. + + * class-create.c: Improve comments. + * obj-copy-out.c: Likewise. + +2004-11-30 Neal H. Walfield <neal@gnu.org> + * cap-server-intern.h (_hurd_cap_obj_drop): Reverse faulty logic. 2004-11-30 Neal H. Walfield <neal@gnu.org> diff --git a/libhurd-cap-server/cap-server.h b/libhurd-cap-server/cap-server.h index b85f3f1..3b3505d 100644 --- a/libhurd-cap-server/cap-server.h +++ b/libhurd-cap-server/cap-server.h @@ -219,19 +219,18 @@ struct hurd_cap_obj /* The reference counter for this object. */ uatomic32_t refs; - /* The state of this object. If this is _HURD_CAP_STATE_GREEN, you - can use the capability object. Otherwise, you should refrain - from using it. You can sleep on the obj_state_cond condition in - the capability class until the state goes back to - _HURD_CAP_STATE_GREEN again. - - If the state is _HURD_CAP_STATE_YELLOW, this means that there is - some thread who wants the state to be _HURD_CAP_STATE_RED, and - this thread canceled all other pending RPC threads on this - object. If you are the last worker thread for this capability - object (except for the thread waiting for the condition to become - _HURD_CAP_STATE_RED), you have to broadcast the obj_state_cond - condition. + /* The state of the capability object. + + If STATE is _HURD_CAP_STATE_GREEN, you can use the capability + object. Otherwise, you must wait on the condition + CAP_CLASS->OBJ_COND for it return to _HURD_CAP_STATE_GREEN. + + If the state is _HURD_CAP_STATE_YELLOW, a thread wants the state + to be _HURD_CAP_STATE_RED (and it has canceled all other pending + RPC threads on this object). The last worker thread for this + capability object (other than the thread waiting for the + condition to become _HURD_CAP_STATE_RED) must broadcast the + obj_state_cond condition. Every worker thread that blocks on the capability object state until it reverts to _HURD_CAP_STATE_GREEN must perform a @@ -259,7 +258,7 @@ struct hurd_cap_obj /* Operations on capability classes. */ /* Create a new capability class for objects with the size SIZE and - alignment requirement ALIGNMENT. + alignment requirement ALIGNMENT (which must be a power of 2). The callback OBJ_INIT is used whenever a capability object in this class is created. The callback OBJ_REINIT is used whenever a @@ -333,19 +332,21 @@ error_t hurd_cap_class_alloc (hurd_cap_class_t cap_class, hurd_cap_obj_t *r_obj); -/* Get the size of the header, given the alignment requirement - ALIGNMENT of the user object following it. */ +/* Get the offset of the user object following a capability. + ALIGNMENT is the alignment requirements of the user object as + supplied to hurd_cap_class_init, hurd_cap_class_init_untyped, + hurd_cap_class_create or hurd_cap_class_create_untyped. */ static inline size_t __attribute__((__always_inline__)) -hurd_cap_obj_get_size (size_t alignment) +hurd_cap_obj_user_offset (size_t alignment) { - size_t obj_size = sizeof (struct hurd_cap_obj); + size_t offset = sizeof (struct hurd_cap_obj); size_t rest = sizeof (struct hurd_cap_obj) % alignment; if (rest) - obj_size += alignment - rest; + offset += alignment - rest; - return obj_size; + return offset; } @@ -360,7 +361,7 @@ hurd_cap_obj_to_user_untyped (hurd_cap_obj_t obj, size_t alignment) { uintptr_t obj_addr = (uintptr_t) obj; - obj_addr += hurd_cap_obj_get_size (alignment); + obj_addr += hurd_cap_obj_user_offset (alignment); return (void *) obj_addr; } @@ -380,7 +381,7 @@ hurd_cap_obj_from_user_untyped (void *obj, size_t alignment) { uintptr_t obj_addr = (uintptr_t) obj; - obj_addr -= hurd_cap_obj_get_size (alignment); + obj_addr -= hurd_cap_obj_user_offset (alignment); return (hurd_cap_obj_t) obj_addr; } @@ -409,7 +410,6 @@ hurd_cap_obj_lock (hurd_cap_obj_t obj) pthread_mutex_lock (&obj->lock); } - /* Unlock the object OBJ, which must be locked. */ static inline void hurd_cap_obj_unlock (hurd_cap_obj_t obj) @@ -418,7 +418,7 @@ hurd_cap_obj_unlock (hurd_cap_obj_t obj) } -/* Add a reference for the capability object OBJ. */ +/* Add a reference to the capability object OBJ. */ static inline void hurd_cap_obj_ref (hurd_cap_obj_t obj) { @@ -426,9 +426,11 @@ hurd_cap_obj_ref (hurd_cap_obj_t obj) } -/* Remove one reference for the capability object OBJ. Note that the - caller must have at least two references for this capability object - when using this function. To release the last reference, +/* Remove one reference for the capability object OBJ, which must be + locked. Note that the caller must have at least two references for + this capability object when using this function. If this reference + is potentially the last reference (i.e. the caller does not hold + either directly or indirectly another reference to OBJ), hurd_cap_obj_drop must be used instead. */ static inline void hurd_cap_obj_rele (hurd_cap_obj_t obj) diff --git a/libhurd-cap-server/class-create.c b/libhurd-cap-server/class-create.c index e60deff..2f4c16a 100644 --- a/libhurd-cap-server/class-create.c +++ b/libhurd-cap-server/class-create.c @@ -29,9 +29,10 @@ #include <hurd/cap-server.h> -/* Create a new capability class for objects with the size SIZE, - including the struct hurd_cap_obj, which has to be placed at the - beginning of each capability object. +/* Create a new capability class for objects allocating SIZE bytes for + the user object with alignment ALIGNMENT (i.e. size does NOT + include the struct hurd_cap_obj which is placed at the beginning of + each capability object). The callback OBJ_INIT is used whenever a capability object in this class is created. The callback OBJ_REINIT is used whenever a diff --git a/libhurd-cap-server/class-init.c b/libhurd-cap-server/class-init.c index 9c7d185..cdbb7db 100644 --- a/libhurd-cap-server/class-init.c +++ b/libhurd-cap-server/class-init.c @@ -97,11 +97,17 @@ hurd_cap_class_init_untyped (hurd_cap_class_t cap_class, { error_t err; - size += hurd_cap_obj_get_size (alignment); + /* The alignment requirements must be a power of 2. */ + assert ((alignment & (alignment - 1)) == 0 + || ! __func__ ": requested alignment not a power of 2"); - /* FIXME: Find the smallest possible alignment common to the user - object and a struct hurd_cap_obj. */ - assert (alignment >= __alignof__(struct hurd_cap_obj)); + /* Find the smallest alignment requirement common to the user object + and a struct hurd_cap_obj. Since both are required to be a power + of 2, we need simply take the larger one. */ + if (alignment < __alignof__(struct hurd_cap_obj)) + alignment = __alignof__(struct hurd_cap_obj); + + size += hurd_cap_obj_user_offset (alignment); /* Capability object management. */ @@ -139,9 +145,8 @@ hurd_cap_class_init_untyped (hurd_cap_class_t cap_class, if (err) goto err_cond; - /* The cond_waiter member doesn't need to be initialized. It is set - whenever the state changes to _HURD_CAP_STATE_YELLOW by the - inhibitor. */ + /* The cond_waiter member doesn't need to be initialized. It is + only valid when CAP_CLASS->STATE is _HURD_CAP_STATE_YELLOW. */ cap_class->pending_rpcs = NULL; diff --git a/libhurd-cap-server/obj-copy-out.c b/libhurd-cap-server/obj-copy-out.c index 6bac033..070b7e0 100644 --- a/libhurd-cap-server/obj-copy-out.c +++ b/libhurd-cap-server/obj-copy-out.c @@ -83,7 +83,7 @@ _hurd_cap_obj_copy_out (hurd_cap_obj_t obj, hurd_cap_bucket_t bucket, return 0; } - /* Add the entry to the caps table of the client. */ + /* Add the entry to the cap table of the client. */ err = hurd_table_enter (&client->caps, &entry, &entry->id); if (err) { |