栏目分类:
子分类:
返回
名师互学网用户登录
快速导航关闭
当前搜索
当前分类
子分类
实用工具
热门搜索
名师互学网 > IT > 软件开发 > 后端开发 > Java

[linux专题]基于linux线程与信号处理

Java 更新时间: 发布时间: IT归档 最新发布 模块sitemap 名妆网 法律咨询 聚返吧 英语巴士网 伯小乐 网商动力

[linux专题]基于linux线程与信号处理

 

目录

1.linux线程

1.1 基本介绍

1.2 线程信息

1.3 线程创建

1.4 线程终止

1.5 线程指定数据

1.5 线程同步

2.linux 信号与信号处理

2.1 信号介绍

2.2 信号种类

2.3 信号处理

2.4 信号发送

2.5 信号屏蔽


1.linux线程

1.1 基本介绍

线程是计算机独立运行的最小单位,也可以看出线程是系统分配CPU资源的基本单位,每个线程在系统给它时间片内,取得CPU的控制权,执行线程中的代码。

相对于进程来说,线程创建消耗资源少,线程切换速度快,进程内的线程数据共享,通信效率高。

1.2 线程信息

线程ID,每个线程有唯一的线程ID

寄存器,如PC计数器,堆栈指针等

堆栈

信号掩码

优先级

线程私有空间等。

1.3 线程创建
#include 

typedef struct
{
    int                   detachstate;     
    int                   schedpolicy;     
    struct sched_param    schedparam;      
    int                   inheritsched;    
    int                   scope;           
    size_t                guardsize;       
    int                   stackaddr_set;   
    void*                 stackaddr;       
    size_t                stacksize;       
}pthread_attr_t;


int pthread_create(pthread_t *thread,pthread_attr_t* attr,void* (*start_routine)(void*),void *arg);


pthread_t pthread_self(void);


int pthread_equal(pthread_t thread1,pthread_t thread2);


int pthread_once(pthread_once_t* once_control,void (*int_routine)(void));

#include 
#include 
#include 
#include 

int* thread_routine(void* arg);

int main(void)
{
    pthread_t thid;

    printf("main thread id is %u rn",pthread_self());

    if (pthread_create(&thid,NULL,(void*)thread_routine,NULL) != 0)
    {
        printf("thread create failed! rn");
        exit(1);
    }
    sleep(1);
    exit(0);
}

int* thread_routine(void* arg);
{
    pthread_t thid;

    thid = pthread_self();
    printf("routine thread id is %u rn",thid);

    return NULL;
}

1.4 线程终止

1> 从线程函数中,通过return返回终止;

2> 调用pthread_exit() 终止线程。

线程终止时的资源释放,如下成对出现的红函数,可以跟着线程的终止而释放资源

#include 

#define pthread_cleanup_push(routine,arg) 
    { struct _pthread_cleanup_buffer buffer; 
             _pthread_cleanup_push(&buffer,(routine),(arg));
#define pthread_cleanup_pop 
             _pthread_cleanup_pop(&buffer,(routine));}

线程间的同步等待

#include 


void pthread_exit(void* ret);


int pthread_join(pthread_t th,void* thread_ret);


int pthread_detach(pthread_t th);

1.5 线程指定数据

线程指定数据(thread specific data TSD),通过键值访问方式,来达到线程私有数据目的。

具体方法是,各个线程,使用公有的键来访问线程数据,而每个线程中使用该键对应的数据是不一致的,以此,达到私有数据访问的目的。

#include 


int pthread_key_create(pthread_key_t *key,void (*destr_function)(void*));


int pthread_setspecific(pthread_key_t key,const void * ptr);


void* pthread_getspecific(pthread_key_t key);


int pthread_key_delete(pthread_key_t key);

1.5 线程同步

同步的方式,主要包含,互斥锁,条件变量,异步信号。

互斥锁

#include 





pthread_mutex_t mutex = PTHREAD_MUTEX_INITIALIZER;


int pthread_mutex_init(pthread_mutex_t *mutex,const pthread_mutexattr_t *mutexattr);


int pthread_mutex_lock(pthread_mutex_t *mutex);


int pthread_mutex_trylock(pthread_mutex_t *mutex);


int pthread_mutex_unlock(pthread_mutex_t *mutex);


int pthread_mutex_destroy(pthread_mutex_t *mutex);


条件变量

#include 


pthread_cond_t cond = PTHREAD_COND_INITIALIZER;


int pthread_cond_init(pthread_cond_t 8cond,pthread_condattr_t *cond_attr);


int pthread_cond_wait(pthread_cond_t *cond,pthread_mutex_t *mutex);


int pthread_cond_timewait(pthread_cond_t *cond,pthread_mutex *mutex,const struct timespec *abstime);


int pthread_cond_signal(pthread_cond_t *cond);


int pthread_cond_broadcast(pthread_cond_t *cond);


int pthread_cond_destroy(pthread_cond_t *cond);

异步信号

#include 


int pthread_kill(pthread_t threadid,int signo);


int pthread_sigmask(int how,const sigset_t *newmask,sigset_t *oldmask);


int sigwait(const sigset_t *set,int *sig);

2.linux 信号与信号处理

2.1 信号介绍

信号是一种软中断,一种处理异步事件的方式,主要用来通知进程发生了事件,以及传递数据。

信号的来源:终端按键,硬件异常,kill、sigqueue发送信号,alarm/timer等发送信号等;

2.2 信号种类

信号说明
SIGHUP用户退出shell,该shell启动的进程收到该信号,默认为退出进程
SIGINT用于按下 CTRL+C 发出该终端启动的程序该信号,默认为终止进程
SIGQUIT用于按下 CTRL+  向正在运行的程序发出该信号,默认终止进程,产生core文件
SIGILLCPU 检测非法指令,终止进程,产生core文件
SIGTRAP断点指令或trap指令产生,终止进程,产生core文件
SIGABRT调用abort函数产生该信号,终止进程,产生core文件
SIGBUS非法访问地址,内存地址对齐出错,终止进程,产生core文件
SIGFPE致命的算术错误,如浮点运算错误,溢出,除0等,终止进程,产生core文件
SIGKILL无条件终止进程,不可被忽略 处理和阻塞
SIGUSR1用户定义信号
SIGSEGV进程进行了无效的内存访问,终止进程,产生core文件
SIGUSR2用户定义信号
SIGPIPEbroken pipe,向一个没有读端的管道写数据
SIGALRM定时器超时,系统调用alarm设置
SIGTERM程序terminate信号,可被阻塞和处理,执行kill是产生这个信号
SIGCHLD子进程结束时,父进程收到该信号,默认忽略该信号
SIGCONT让一个暂停的进程继续执行
SIGSTOPstop 进程的执行,只是让进程暂停,不可被忽略处理和阻塞
SIGTSTP停止进程的运行,可被处理和忽略, 一般CTRL+Z发出,默认为暂停进程
SIGTTIN后台进程从用户终端读数据,终端进程收到该信号,默认暂停进程
SIGTTOU后台进程从用户终端写数据,终端进程收到该信号,默认暂停进程
SIGURG套接字 socket有紧急数据时,向正在运行的进程发出该信号,默认动作为忽略
SIGXCPU进程执行时间超过分配给该进程的CPU时间,默认为终止进程
SIGXFSZ超过文件最大长度限制,终止进程,产生core文件
SIGVTALRM虚拟时钟超时,默认动作终止进程
SIGPROF同SIGVTALRM
SIGWINCH窗口大小改变发出,默认忽略该信号
SIGIO异步IO事件,默认忽略
SIGPWR关机,默认终止进程
SIGSYS无效的系统调用,终止进程,产生core文件
SIGRTMIN~SIGRTMAX linux 实时信号,无固定意义
1~31 不可靠信号33~64 可靠信号,不会丢失
优先级实时信号,值越小,优先级越高

2.3 信号处理
#include 

typedef void (*sighandler_t)(int);

struct sigaction
{
    void (*sa_handler)(int);                       
    void (*sa_sigaction)(int,siginfo_t*,void*);    
    sigset_t sa_mask;                                  
    int sa_flags;
    void (*sa_restorer)(void);                     
};


sighandler_t signal(int signum,sighandler_t handler);


int sigaction(int signum,const struct sigaction *act,struct sigaction *oldact);
#include 
#include 
#include 

int tmp = 0;
void sigint_handler(int signo);

int main(void)
{
    struct sigaction act;
    
    act.sa_handler = sigint_handler;
    act.sa_flags = SA_NOMASK;

    sigaction(SIGINT,&act,NULL);
    
    while(1);

    exit(0);
}

void sigint_handler(int signo)
{
    printf("recv SIGINTn");
    sleep(5);
    tmp++;
    printf("tmp value is %d n",tmp);
}

执行以上程序,按CTRL+C 出现效果,按CTRL+ 退出

#include 


int pause(void);

2.4 信号发送

kill 函数发送

int kill(pid_t pid,int sig);

 pid>0 发送给指定pid信号

pid=0,发送给进程组

pid=-1 广播给除init和自身的所有进程

pid < -1,进程组-pid的所有进程

raise函数发送

int raise(ing sig);

sigqueue函数发送

int sigqueue(pid_t pid,int sig,const union sigval var);

支持带参数的发送信号 

alarm函数发送

unsigned int alarm(unsigned int seconds);

按设定的时间发送SIGALRM信号

abort函数发送

void abort(void);

发送SIGABRT信号

2.5 信号屏蔽

int sigprocmask(int how,const sigset_t *set,sigset_t *oldset);

how,主要包含如下设置

SIG_BLOCK,设置为信号集并集 set| oldset

SIG_SETMASK,设置为set

int sigpending(sigset_t *set);

获取当点pending的信号集

int sigsuspend(const sigset_t *mask)

将信号屏蔽码设置为mask,和pause一样,等待信号的发生并执行信号处理函数。

转载请注明:文章转载自 www.mshxw.com
本文地址:https://www.mshxw.com/it/657587.html
我们一直用心在做
关于我们 文章归档 网站地图 联系我们

版权所有 (c)2021-2022 MSHXW.COM

ICP备案号:晋ICP备2021003244-6号