4,436
社区成员
发帖
与我相关
我的任务
分享
#ifndef __LINUX_SEMAPHORE_H
#define __LINUX_SEMAPHORE_H
#include <linux/list.h>
#include <linux/spinlock.h>
/* Please don't access any members of this structure directly */
struct semaphore {
spinlock_t lock;
unsigned int count;
struct list_head wait_list;
};
#define __SEMAPHORE_INITIALIZER(name, n) \
{ \
.lock = __SPIN_LOCK_UNLOCKED((name).lock), \
.count = n, \
.wait_list = LIST_HEAD_INIT((name).wait_list), \
}
#define DECLARE_MUTEX(name) \
struct semaphore name = __SEMAPHORE_INITIALIZER(name, 1)
static inline void sema_init(struct semaphore *sem, int val)
{
static struct lock_class_key __key;
*sem = (struct semaphore) __SEMAPHORE_INITIALIZER(*sem, val);
lockdep_init_map(&sem->lock.dep_map, "semaphore->lock", &__key, 0);
}
#define init_MUTEX(sem) sema_init(sem, 1)
#define init_MUTEX_LOCKED(sem) sema_init(sem, 0)
u can tell both DECLARE_MUTEX and init_MUTEX are defined as macros, which is different than LDD3's description, probably because LDD3 was published in 2005. And you can also tell both of them eventually requires __SEMAPHORE_INITIALIZER to initialize the semaphore variable. Even the function sema_init is declared as "inline", which basically tells the compiler: don't make me as a function if you don't have to...
so, I would say there is no difference at all. You may think there is a subtle difference: by calling init_MUTEX, you could though, manipulate the variable before or afterward since it's defined in your source. However, DECLARE_MUTEX allows you to do the same thing, but it's vague, since no declaration can be found in your source for this variable...
struct semaphore {
spinlock_t lock;
unsigned int count;
struct list_head wait_list;
};
#define __SEMAPHORE_INITIALIZER(name, n) \
{ \
.lock = __SPIN_LOCK_UNLOCKED((name).lock), \
.count = n, \
.wait_list = LIST_HEAD_INIT((name).wait_list), \
}
#define DECLARE_MUTEX(name) \
struct semaphore name = __SEMAPHORE_INITIALIZER(name, 1)
static inline void sema_init(struct semaphore *sem, int val)
{
static struct lock_class_key __key;
*sem = (struct semaphore) __SEMAPHORE_INITIALIZER(*sem, val);
lockdep_init_map(&sem->lock.dep_map, "semaphore->lock", &__key, 0);
}
#define init_MUTEX(sem) sema_init(sem, 1)
#define init_MUTEX_LOCKED(sem) sema_init(sem, 0)
in this version (kernel 2.6.31.13 ) of the implementation of semaphore, both DECLARE_MUTEX and init_MUTEX are actually macros and both of them refers the same macro "__SEMAPHORE_INITIALIZER" to initialize the semaphore variable. sema_init. as the function expanded by init_MUTEX is declared as inline, which basically tells the compiler: don't make me as a function call if you could...
there is actually not much difference at all. One subtle difference though, is, by init_MUTEX, you could manipulate the semaphore variable by your own, since you define it and send its address to init_MUTEX for initialization. With DECLARE_MUTEX, you could do the same, but it's vague, since the reader can't find the declaration of this variable...