Linux下线程与进程同步与互斥

线程同步

1. semophore 信号量

接口函数

int    sem_destroy(sem_t *);
int    sem_getvalue(sem_t *restrict, int *restrict);
int    sem_init(sem_t *, int, unsigned);
int    sem_post(sem_t *);

int    sem_timedwait(sem_t *restrict, const struct timespec *restrict);

int    sem_trywait(sem_t *);
int    sem_wait(sem_t *);

简单用法:
#include <semaphore.h>
sem_t bin_sem; 
res = sem_init(&bin_sem, 0, 0);
sem_wait(&bin_sem);              //对应于P(sem)操作
//do something
sem_post(&bin_sem);              //对应于V(sem)操作
sem_destroy(&bin_sem);

2. Mutex 互斥
头文件以及函数
#include <pthread.h>
int pthread_mutex_init(pthread_mutex_t *mutex, const pthread_mutexattr_t *mutexattr);
int pthread_mutex_lock(pthread_mutex_t *mutex));

int pthread_mutex_timedlock(pthread_mutex_t *, const struct timespec *);

int pthread_mutex_trylock(pthread_mutex_t *);
int pthread_mutex_unlock(pthread_mutex_t *mutex);
int pthread_mutex_destroy(pthread_mutex_t *mutex);

使用

pthread_mutex_t mutex;

pthread_mutex_init(&mutex,NULL);

pthread_mutex_lock(&mutex);

//do something

pthread_mutex_unlock(&mutex);

3.条件变量

int pthread_cond_broadcast(pthread_cond_t *);

int pthread_cond_destroy(pthread_cond_t *);

int pthread_cond_init(pthread_cond_t *restrict, const pthread_condattr_t *restrict);

int pthread_cond_signal(pthread_cond_t *);

int pthread_cond_timedwait(pthread_cond_t *restrict, pthread_mutex_t *restrict, const struct timespec *restrict);

int pthread_cond_wait(pthread_cond_t *restrict, pthread_mutex_t *restrict);

互斥量与条件变量经常一起使用,实现生产者与消费者之间的同步与互斥。

例如多个生产者,多个消费者都对同一缓存区进行操作的情况。

#include <pthread.h>

struct data{};   //数据块

int n;              //缓存区数据块个数

pthread_mutex_t mutex = PTHREAD_MUTEX_INITIALIZER;  //缓存区互斥访问

pthread_mutex_t mutex_n = PTHREAD_MUTEX_INITIALIZER;  //对n的互斥访问

pthread_cond_t wcond = PTHREAD_COND_INITIALIZER;     //写条件变量

pthread_cond_t rcond = PTHREAD_COND_INITIALIZER;      //读条件变量

//初始化操作

n = 10;   //假设缓存区有10个数据块

produce线程函数

                pthread_mutex_lock(&mutex_n);

                //线程同步,若缓存区满则等待消费者取走数据

                while(n <= 0)

                  pthread_cond_wait(&wcond,&mutex_n);

                pthread_mutex_lock(&mutex);           //缓存区有空闲,申请访问缓存区

                //对缓存区操作

                pthread_mutex_unlock(&mutex);

                //写完成,唤醒读进程

                pthread_cond_signal(&rcond);

                //对缓存区状态信息修改

                n--;                    //很重要 同步的问题

                pthread_mutex_unlock(&mutex_n);

 

customer线程函数

 

                pthread_mutex_lock(&mutex_n);

                //线程同步,若缓存区空等待生产者写入数据

                while(n >= 10)

                        pthread_cond_wait(&rcond,&mutex_n);

                pthread_mutex_lock(&mutex);               //不为空,申请访问缓存区

                 //从一个有效缓存区消费

                pthread_mutex_unlock(&mutex);

                //取走数据,唤醒生产者

                pthread_cond_signal(&wcond);

                //更改状态信息

                n++;   //很重要 确保消费成功再更改状态     

                pthread_mutex_unlock(&mutex_n);

 

4.读写锁

读写锁与互斥量类似,不过读写锁允许更高的并行性。

当读写锁是加锁状态时,在这个锁被解锁之前,所有试图对这个锁加锁的线程都会被阻塞。

当读写锁在读加锁状态时,所有试图以读模式对它进行加锁的线程都可以得到访问权,但写锁需等待所有读锁全部释放。

int pthread_rwlock_destroy(pthread_rwlock_t *);

int pthread_rwlock_init(pthread_rwlock_t *restrict, const pthread_rwlockattr_t *restrict);

int pthread_rwlock_rdlock(pthread_rwlock_t *);

int pthread_rwlock_timedrdlock(pthread_rwlock_t *restrict, const struct timespec *restrict);

int pthread_rwlock_timedwrlock(pthread_rwlock_t *restrict, const struct timespec *restrict);

int pthread_rwlock_tryrdlock(pthread_rwlock_t *);

int pthread_rwlock_trywrlock(pthread_rwlock_t *);

int pthread_rwlock_unlock(pthread_rwlock_t *);

int pthread_rwlock_wrlock(pthread_rwlock_t *);

5. Spinlocks 自旋锁


int pthread_spin_destroy(pthread_spinlock_t *);

int pthread_spin_init(pthread_spinlock_t *, int);

int pthread_spin_lock(pthread_spinlock_t *);

int pthread_spin_trylock(pthread_spinlock_t *);

int pthread_spin_unlock(pthread_spinlock_t *);

进程同步/通信

POSIX IPC实现

1. Semaphore 信号量
简单过程:
semaphore sv = 1;
loop forever {
P(sv);
critical code section;
V(sv);
noncritical code section;
}
头文件以及函数:
#include <sys/sem.h>
int semctl(int sem_id, int sem_num, int command, ...);
int semget(key_t key, int num_sems, int sem_flags);
int semop(int sem_id, struct sembuf *sem_ops, size_t num_sem_ops);

2.Share Memory 共享内存
头文件以及函数
#include <sys/shm.h>
void *shmat(int shm_id, const void *shm_addr, int shmflg);
int shmctl(int shm_id, int cmd, struct shmid_ds *buf);
int shmdt(const void *shm_addr);
int shmget(key_t key, size_t size, int shmflg);

3.Message Queues 消息队列
头文件以及函数
#include <sys/msg.h>
int msgctl(int msqid, int cmd, struct msqid_ds *buf);
int msgget(key_t key, int msgflg);
int msgrcv(int msqid, void *msg_ptr, size_t msg_sz, long int msgtype, int msgflg);
int msgsnd(int msqid, const void *msg_ptr, size_t msg_sz, int msgflg);

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值