mysleep与竞态条件下的mysleep

1.编写代码实现sleep功能
利用pause()和alarm()函数来实现
<1> 用alarm()设置闹钟

#include<unistd.h>
unsigned int alarm(unsigned seconds);

alarm函数可以设置一个闹钟,及让内核在seconds秒之后发送一个SIGALRM信号该信号的默认处理动作是终止该进程;
<2> 用pause()等待,内核切换到其他进程运行

#include<unistd.h>
int pause(void)

pause函数使调⽤进程挂起直到有信号递达。如果信号的处理动作是终⽌进程,则进程终⽌,pause函数没有机会返回;如果信号的处理动作是忽略,则进程继续处于挂起状态,pause不返回;如果信号的处理动作是捕捉,则调⽤了信号处理函数之后pause返回-1,errno设置为EINTR, 所以pause只有出错的返回值。

//mysleep代码
#include<stdio.h>
#include<unistd.h>
#include<signal.h>

void sig_alrm()
{

}

unsigned int mysleep(unsigned int nsecs)
{
     struct sigaction new,old;
     unsigned int unslept = 0;                                                                       
     new.sa_handler=sig_alrm;
     sigemptyset(&new.sa_mask);
     new.sa_flags=0;
     sigaction(SIGALRM,&new,&old);//注册信号处理函数
     alarm(nsecs);//设置闹钟
     pause();
     unslept=alarm(0);//清空闹钟
     sigaction(SIGALRM,&old,NULL);//恢复默认信号处理函数
     return unslept;
 }
  int main()
 {
    while(1)
     {
         mysleep(1);
        printf("5 second passed\n");
     }
     return 0;
}                                                                                               

<3> sigaction函数

#include <signal.h>
int sigaction(int signo, const struct sigaction *act, struct sigaction *oact);

sigaction函数可以读取和修改与指定信号相关联的处理动作。调⽤成功则返回0,出错则返回- 1。 signo是指定信号的编号。若act指针⾮空,则根据act修改该信号的处理动作。若oact指针⾮ 空,则通过oact传出该信号原来的处理动作。
sigaction结构体:

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

2.竞态条件下mysleep

#include<stdio.h>
#include<unistd.h>
#include<signal.h>

void sig_alrm()
{

}

unsigned int mysleep(unsigned int nsecs)
{
     struct sigaction new,old;
     sigset_t newmask,oldmask,suspmask;

     unsigned int unslept = 0;
     new.sa_handler=sig_alrm;
     sigemptyset(&new.sa_mask);
     new.sa_flags=0;
     sigaction(SIGALRM,&new,&old);
     sigemptyset(&newmask);
     sigaddset(&newmask,SIGALRM);
     sigprocmask(SIG_BLOCK,&newmask,&oldmask);
     alarm(nsecs);
     suspmask=oldmask;
     sigdelset(&suspmask,SIGALRM);
     sigsuspend(&suspmask);

     unslept=alarm(0);
     sigaction(SIGALRM,&old,NULL);
    sigprocmask(SIG_SETMASK,&oldmask,NULL);
     return unslept;
 }
 int main()
 {
     while(1)
     {
         mysleep(1);
         printf("5 second passed\n");
     }
     return 0;
 }                  
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值