zoukankan      html  css  js  c++  java
  • UNIX环境高级编程8.9竞争条件

    这一节,书中的TELL_WAIT与TELL_PARENT,TELL_CHILD没有弄清楚,到底是如何实现的同步机制。

    3P4O[{]11ULCN6O9L~2AB7E

    ]S2GB33L5{B28LBWYAI2E@5

    $1PGJEVM%`17H@3YC@UPI`Q

    // proc/tellwait1.c 8-6
    #include "apue.h"
    
    static void charatatime(const char *);
    
    int main(void)
    {
        pid_t pid;
    
        if ((pid = fork()) < 0)
        {
            err_sys("fork error");
        }
        else if (pid == 0)
        {
            charatatime("output from child
    ");
        }
        else
        {
            charatatime("output from parent
    ");
        }
        return 0;
    }
    
    static void charatatime(const char* str)
    {
        const char* ptr;
        int c;
    
        setbuf(stdout, NULL); /* set unbuffered */
        for (ptr = str; (c = *ptr++) != 0; )
        {
            putc(c, stdout);
        }
    }
    

    Q31U_3F)A39TP]~Z}$R0[PI

    // lib/tellwait.c
    #include "apue.h"
    
    static volatile sig_atomic_t sigflag; /* set nonzero by sig handler */
    static sigset_t newmask, oldmask, zeromask;
    
    static void sig_usr(int signo)	/* one signal handler for SIGUSR1 and SIGUSR2 */
    {
    	sigflag = 1;
    }
    
    void TELL_WAIT(void)
    {
        if (signal(SIGUSR1, sig_usr) == SIG_ERR)
        {
            err_sys("signal(SIGUSR1) error");
        }
        if (signal(SIGUSR2, sig_usr) == SIG_ERR)
        {
            err_sys("signal(SIGUSR2) error");
        }
        sigemptyset(&zeromask);
        sigemptyset(&newmask);
        sigaddset(&newmask, SIGUSR1);
        sigaddset(&newmask, SIGUSR2);
    
        /*
         * Block SIGUSR1 and SIGUSR2, and save current signal mask.
         */
        if (sigprocmask(SIG_BLOCK, &newmask, &oldmask) < 0)
        {
            err_sys("SIG_BLOCK error");
        }
    }
    
    void
    TELL_PARENT(pid_t pid)
    {
    	kill(pid, SIGUSR2);		/* tell parent we're done */
    }
    
    void WAIT_PARENT(void)
    {
    	while (sigflag == 0)
        {
            sigsuspend(&zeromask);	/* and wait for parent */
        }
    	sigflag = 0;
    
    	/*
    	 * Reset signal mask to original value.
    	 */
    	if (sigprocmask(SIG_SETMASK, &oldmask, NULL) < 0)
        {
            err_sys("SIG_SETMASK error");
        }
    }
    
    void TELL_CHILD(pid_t pid)
    {
    	kill(pid, SIGUSR1);			/* tell child we're done */
    }
    
    void WAIT_CHILD(void)
    {
    	while (sigflag == 0)
    		sigsuspend(&zeromask);	/* and wait for child */
    	sigflag = 0;
    
    	/*
    	 * Reset signal mask to original value.
    	 */
    	if (sigprocmask(SIG_SETMASK, &oldmask, NULL) < 0)
    		err_sys("SIG_SETMASK error");
    }
    
    // proc/tellwait2.c 8-7
    #include "apue.h"
    
    static void charatatime(const char*);
    
    int main()
    {
        pid_t pid;
    
        TELL_WAIT();
    
        if ((pid = fork()) < 0)
        {
            err_sys("fork error");
        }
        else if (pid == 0)
        {
            WAIT_PARENT(); /* parent goes first */
            charatatime("output from child
    ");
        }
        else
        {
            charatatime("output from parent
    ");
            TELL_CHILD(pid);
        }
        return 0;
    }
    
    static void charatatime(const char* str)
    {
        const char* ptr;
        int c;
    
        setbuf(stdout, NULL); /* set unbuffered */
        for (ptr = str; (c = *ptr++) != 0; )
        {
            putc(c, stdout);
        }
    }
    

    D7G_))HEX@AR1AY17M86JCL

    // proc/tellwait3.c
    #include "apue.h"
    
    static void charatatime(const char*);
    
    int main()
    {
        pid_t pid;
    
        TELL_WAIT();
    
        if ((pid = fork()) < 0)
        {
            err_sys("fork error");
        }
        else if (pid == 0)
        {
            charatatime("output from child
    ");
            TELL_PARENT(getppid()); /* parent goes first */
        }
        else
        {
            WAIT_CHILD();
            charatatime("output from parent
    ");
        }
        return 0;
    }
    
    static void charatatime(const char* str)
    {
        const char* ptr;
        int c;
    
        setbuf(stdout, NULL); /* set unbuffered */
        for (ptr = str; (c = *ptr++) != 0; )
        {
            putc(c, stdout);
        }
    }
    

    2e5bc8d8-11ce-4321-b15a-f1f6009be7ca

  • 相关阅读:
    Java设计模式(学习整理)---工厂模式
    Java Swing 使用总结(转载)
    Java-生成验证码图片(自定义内容,尺寸,路径)
    二维码(带有图片)的生成
    J2se中的声音---AudioPlayer
    文件的读取和写入(指定路径)
    ASP.NET:使用Flurl制作可复用的分页组件
    ASP.NET:Forms身份验证和基于Role的权限验证
    ASP.NET:MVC模板化机制
    ASP.NET:MVC中文件上传与地址变化处理
  • 原文地址:https://www.cnblogs.com/sunyongjie1984/p/4276923.html
Copyright © 2011-2022 走看看