加锁和互斥的目的是为了保护共享资源(数据或外设地址)不被多个线程同时访问,而不是保护代码被同时执行
一、信号量
信号量为1表示资源可用,为0表示资源不可用,对信号量的加减主要涉及PV操作,进入临界区调用P操作(down)将信号量减1,推出临界区调用V操作(up)将信号量加1.
1. 信号量的实现
struct semaphore *sem;
void semaphore_init(struct semaphore *sem, int val);
互斥锁是一种简单的信号量,它的值只有0和1,但是信号量的值可以是更大的值,表示有多个线程在使用临界区的资源
DECLARE_MUTEX(name);
DECLARE_MUTEX_LOCKED(name);
void init_MUTEX(struct semaphore *sem);
void init_MUTEX_LOCKED(struct semaphore *sem);
void down(struct semaphore *sem); //
int down_interruptible(struct semaphore *sem); //可以中断
int down_trylock(struct semaphore *sem); // 不可以睡眠
信号量可以指定获取信号的线程是否可以被中断
2. Completions 机制
在使用信号量对临界区进行加锁的时候,如果一旦解锁,那么所有想要进入临界区的线程就会开始对这个临界区的使用权进行抢占,这个时候就会出现线程之间相互竞争的情况,这样就会导致性能受损。所以提出了一种completion机制,它允许一个线程告诉另一个线程工作已经完成.
DECLARE_COMPLETION(my_completion); //定义一个completion
void wait_for_completion(struct completion *c); //这个函数进行一个不