国产 无码 综合区,色欲AV无码国产永久播放,无码天堂亚洲国产AV,国产日韩欧美女同一区二区

Linux進程通信:無名管道

這篇具有很好參考價值的文章主要介紹了Linux進程通信:無名管道。希望對大家有所幫助。如果存在錯誤或未考慮完全的地方,請大家不吝賜教,您也可以點擊"舉報違法"按鈕提交疑問。

進程通信目的:

(1)數(shù)據傳輸:進程間數(shù)據傳輸;

(2)通知事件:一個進程向另一個或一組進程發(fā)送消息,通知某個事件的發(fā)生(如子進程終止時需通知父進程);

(3)資源共享:多個進程共享資源,需要內核提供同步互斥機制;

(4)進程控制:某進程需要控制另一個進程的執(zhí)行(如Debug進程),此時控制進程需要攔截另一個進程的所有陷入、異常、狀態(tài)等。

進行通信分類及方式:

Linux進程通信:無名管道


無名管道

特點:(1)半雙工。數(shù)據同一時刻只能單向傳輸;

? ? ? ? ? ?(2)數(shù)據從管道一端寫入,另一端讀出;

? ? ? ? ? ?(3)寫入管道的數(shù)據遵循先進先出;

? ? ? ? ? ?(4)管道非普通文件,不屬于某個文件系統(tǒng),只存在于內存;

? ? ? ? ? ?(5)無名管道只能在具有公共祖先的進程(父子進程、兄弟進程等)之間使用。


(1)pipe函數(shù):創(chuàng)建無名管道

#include<unistd.h>

int pipe(int pipefd[2]);
/*
功能:
    創(chuàng)建無名管道。
參數(shù):
    pipefd:int型數(shù)組的首地址,存放了管道文件描述符pipefd[0]、pipefd[1]。
            pipefd[0]用于讀管道,pipefd[1]用于寫管道。
            一般的文件I/O函數(shù)都可用來操作管道(lseek除外)。
返回值:
    成功:0
    失?。?1
*/

pipe示例:

#include<stdio.h>
#include<stdlib.h>
#include<string.h>
#include<unistd.h>

int test() {
    int fds[2];  // fds[0]用于讀管道,fds[1]用于寫管道
    int ret = -1;

    // 創(chuàng)建一個無名管道
    ret = pipe(fds);
    if (-1 == ret) {
        perror("pipe");
        return 1;
    }

    printf("讀管道的文件描述符:%d, 寫管道的文件描述符:%d\n", fds[0], fds[1]);

    // 關閉文件描述符
    close(fds[0]);
    close(fds[1]);
    return 0;
}

運行結果:

Linux進程通信:無名管道


(2)父子進程使用無名管道通信原理:

Linux進程通信:無名管道

a)需要在fork之前創(chuàng)建無名管道,然后子進程也有自己的讀寫管道描述符關聯(lián)無名管道;

b)父進程給子進程發(fā)消息:父進程寫管道、子進程讀管道;需要關閉父進程的讀端文件描述符(fds[0])、子進程的寫端文件描述符(fds[1])。 反之類似。

c)管道默認為阻塞,讀不到內容則阻塞等待有內容可讀;可設置為非阻塞。


(3)管道讀寫特性:

case 1:

? ? ? ? a)若寫端打開,管道中無數(shù)據,讀端進程會阻塞;

? ? ? ? b)若寫端打開,管道中有數(shù)據,讀端進程將數(shù)據讀出,下次若無數(shù)據可讀則阻塞;

case 2:

? ? ? ? 若寫端關閉,讀端進程讀取全部內容后,返回0;

case 3:

? ? ? ? 若讀端打開,管道被寫滿,則寫端進程阻塞;

case 4:

? ? ? ? 若讀端關閉,寫端進程收到一個信號,然后退出。

查看管道大小:

Linux進程通信:無名管道


(4)父子進程使用無名管道通信示例:

#include<stdio.h>
#include<stdlib.h>
#include<string.h>
#include<unistd.h>
#include<sys/types.h>

#define SIZE 64

int main(int argc, const char* argv[]) {

    int ret = -1;
    int fds[2];
    pid_t pid = -1;
    char buf[SIZE];

    // 1. 創(chuàng)建無名管道
    ret = pipe(fds);
    if (-1 == ret) {
        perror("pipe");
        return 1;
    }

    // 2. 創(chuàng)建子進程。需要在創(chuàng)建無名管道之后
    pid = fork();
    if (-1 == pid) {
        perror("fork");
        return 1;
    }

    // 子進程 讀管道
    if (0 == pid) {
        close(fds[1]);  // 關閉寫端

        ret = read(fds[0], buf, SIZE); // 讀管道
        if (ret < 0) {
            perror("read");
            exit(-1);
        }

        printf("子進程讀到的內容:%s\n", buf);

        close(fds[0]);  // 關閉讀端
        exit(0); // 子進程退出
    }

    // 父進程 寫管道
    close(fds[0]); // 關閉讀端

    ret = write(fds[1], "ABCDEFG", 7);  // 寫管道
    if (-1 == ret) {
        perror("write");
        return 1;
    }
    printf("父進程寫了%d字節(jié).\n", ret);
    close(fds[1]);  // 關閉寫端

    return 0;
}

運行結果:

Linux進程通信:無名管道


(5)fpathconf函數(shù):查看管道緩沖區(qū)

#include<unistd.h>

long fpathconf(int fd, int name);
/*
功能:
    通過name查看管道緩沖區(qū)的不同屬性
參數(shù):
    fd:讀端或寫端文件描述符
    name:
        _PC_PIPE_BUF:查看管道緩沖區(qū)大小
        _PC_NAME_MAX:文件名字節(jié)數(shù)上限
返回值:
    成功:屬性值
    失?。?1
*/

fpathconf示例:

#include<stdio.h>
#include<stdlib.h>
#include<string.h>
#include<unistd.h>
#include<sys/types.h>

int main(int argc, const char* argv[]) {

    int fds[2];
    int ret = -1;

    ret = pipe(fds);
    if (-1 == ret) {
        perror("pipe");
        return 1;
    }

    printf("讀端緩沖區(qū)大小:%ld,\n寫端緩沖區(qū)大?。?ld,\n讀端文件名字節(jié)數(shù)上限:%ld,\n寫端文件名字節(jié)數(shù)上限:%ld\n",
        fpathconf(fds[0], _PC_PIPE_BUF), fpathconf(fds[1], _PC_PIPE_BUF),
        fpathconf(fds[0], _PC_NAME_MAX), fpathconf(fds[1], _PC_NAME_MAX));

    return 0;
}

運行結果:

Linux進程通信:無名管道


(6)管道讀端緩沖區(qū)設置為非阻塞的方法:

// 獲取讀端緩沖區(qū)原先的狀態(tài)標記flags 
int flags = fcntl(fd[0], F_GETFL); 

// 設置新狀態(tài)標記flags加入非阻塞狀態(tài)
flags |= O_NONBLOCK;

// 給讀端緩沖區(qū)設置新狀態(tài)標記
fcntl(fd[0], F_SETFL, flags);

讀端設置為非阻塞,若無數(shù)據,讀進程直接返回-1.

讀端以非阻塞的方式讀管道示例:

#include<stdio.h>
#include<stdlib.h>
#include<string.h>
#include<unistd.h>
#include<fcntl.h>
#include<sys/types.h>

#define SIZE 64

int main(int argc, const char* argv[]) {

    int ret = -1;
    int fds[2];
    pid_t pid = -1;
    char buf[SIZE];

    // 1. 創(chuàng)建無名管道
    ret = pipe(fds);
    if (-1 == ret) {
        perror("pipe");
        return 1;
    }

    // 2. 創(chuàng)建子進程。需要在創(chuàng)建無名管道之后
    pid = fork();
    if (-1 == pid) {
        perror("fork");
        return 1;
    }

    // 子進程 讀管道
    if (0 == pid) {
        close(fds[1]);  // 關閉寫端

        /*設置讀端非阻塞*/
        ret = fcntl(fds[0], F_GETFL);  // 獲取讀端緩沖區(qū)狀態(tài)
        ret |= O_NONBLOCK; //將讀端緩沖區(qū)加入非阻塞狀態(tài)
        fcntl(fds[0], F_SETFL, ret); // 將新狀態(tài)設置進入

        ret = read(fds[0], buf, SIZE); // 讀管道
        if (ret < 0) {
            perror("read");
            exit(-1);
        }

        printf("子進程讀到的內容:%s\n", buf);

        close(fds[0]);  // 關閉讀端
        exit(0); // 子進程退出
    }

    // 父進程 寫管道
    sleep(1);
    close(fds[0]); // 關閉讀端

    ret = write(fds[1], "ABCDEFG", 7);  // 寫管道
    if (-1 == ret) {
        perror("write");
        return 1;
    }
    printf("父進程寫了%d字節(jié).\n", ret);
    close(fds[1]);  // 關閉寫端

    return 0;
}

運行結果:

Linux進程通信:無名管道文章來源地址http://www.zghlxwxcb.cn/news/detail-423587.html

到了這里,關于Linux進程通信:無名管道的文章就介紹完了。如果您還想了解更多內容,請在右上角搜索TOY模板網以前的文章或繼續(xù)瀏覽下面的相關文章,希望大家以后多多支持TOY模板網!

本文來自互聯(lián)網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。如若轉載,請注明出處: 如若內容造成侵權/違法違規(guī)/事實不符,請點擊違法舉報進行投訴反饋,一經查實,立即刪除!

領支付寶紅包贊助服務器費用

相關文章

  • 【Linux】進程間通信(匿名管道 & 命名管道)-- 詳解

    【Linux】進程間通信(匿名管道 & 命名管道)-- 詳解

    如何理解進程間通信? 進程具有獨立性,所以進程想要通信難度是比較大的,成本高。 在日常生活中,通信的本質是傳遞信息,但站在程序員角度來看, 進程間通信的本質:讓不同的進程看到同一份資源(內存空間) 。 進程間通信就是進程之間互相傳遞數(shù)據,那么進程間

    2024年04月28日
    瀏覽(26)
  • Linux——進程間通信、管道

    Linux——進程間通信、管道

    進程間的通信就是 在不同進程之間傳播或交換信息。 舉個例子: 古時,兩軍交戰(zhàn)不斬來使; 因為兩軍互相是獨立的,所以使節(jié)就是兩軍之間傳話的進行傳話的; 而在OS中,進程之間也是相互獨立的,但某項工作并不是一個進程就可以完成,而是多個進程之間相互協(xié)助完成;

    2024年02月22日
    瀏覽(23)
  • linux——進程間通信——管道

    linux——進程間通信——管道

    ??1主頁::我的代碼愛吃辣 ??2知識講解:Linux——進程間通信——管道通信 ??3開發(fā)環(huán)境:Centos7 ??4前言:進程間通信(InterProcess Communication,IPC)是指在不同進程之間傳播或交換信息。 目錄 一.什么是進程間通信 二.進程間通信目的 ?三.進程間通信發(fā)展 四.什么是管道

    2024年02月08日
    瀏覽(40)
  • Linux——進程間通信&&管道

    Linux——進程間通信&&管道

    ??北塵_ :個人主頁 ??個人專欄 :《Linux操作系統(tǒng)》《經典算法試題 》《C++》 《數(shù)據結構與算法》 ??走在路上,不忘來時的初心 數(shù)據傳輸:一個進程需要把他的數(shù)據傳給另外一個進程。 資源共享:多個進程之間共享同樣的資源。 通知事件:一個進程需要向另一個或一組

    2024年04月09日
    瀏覽(27)
  • Linux——進程間通信(管道)

    Linux——進程間通信(管道)

    目錄 進程通信的目的 管道 見見豬跑(舉個例子) 文件描述符fd與管道的關系(深度理解管道) 什么是管道? ?匿名管道 pipe函數(shù)概述 父子進程通信時與文件描述符的關系圖(理解pipe函數(shù)的關鍵) pipe函數(shù)的使用 ?管道讀寫規(guī)則 管道的大小 自測 ?使用man 7 pipe查看 使用ulimit -a查看 管

    2024年02月03日
    瀏覽(17)
  • 【Linux】進程通信 — 管道

    【Linux】進程通信 — 管道

    從本章開始,我們開始學習進程通信相關的知識,本章將來詳細探討一下管道,學習匿名管道和命名管道的原理和代碼實現(xiàn)等相關操作。目標已經確定,接下來就要搬好小板凳,準備開講了…???????? 在我們之前的學習中,我們知道進程是具獨立性的。但是不要以為進程

    2024年02月16日
    瀏覽(17)
  • [Linux]進程間通信--管道

    [Linux]進程間通信--管道

    數(shù)據傳輸:一個進程需要將它的數(shù)據發(fā)送給另一個進程 。 資源共享:多個進程之間共享同樣的資源。 通知事件:一個進程需要向另一個或一組進程發(fā)送消息,通知它(它們)發(fā)生了某種事件(如進程終止時要通知父進程)。 進程控制:有些進程希望完全控制另一個進程的執(zhí)

    2024年02月09日
    瀏覽(16)
  • Linux多進程(二)進程通信方式一 管道

    Linux多進程(二)進程通信方式一 管道

    管道的是進程間通信(IPC - InterProcess Communication)的一種方式,管道的本質其實就是內核中的一塊內存(或者叫內核緩沖區(qū)),這塊緩沖區(qū)中的數(shù)據存儲在一個環(huán)形隊列中,因為管道在內核里邊,因此我們不能直接對其進行任何操作。 因為管道數(shù)據是通過隊列來維護的,我們先

    2024年04月29日
    瀏覽(16)
  • Linux進程間通信【命名管道】

    Linux進程間通信【命名管道】

    ?個人主頁: 北 海 ??所屬專欄: Linux學習之旅 ??操作環(huán)境: CentOS 7.6 阿里云遠程服務器 命名管道通信屬于 IPC 的其中一種方式,作為管道家族,命名管道的特點就是 自帶同步與互斥機制、數(shù)據單向流通 ,與匿名管道不同的是:命名管道有自己的名字,因此可以被沒有血

    2024年02月08日
    瀏覽(41)
  • 【Linux】進程間通信——命名管道

    【Linux】進程間通信——命名管道

    匿名管道只能用來進行進程間通信,讓具有血緣關系的進程進行通信 讓毫不相關的進程之間進行通信,就需要采用命名管道通信 因為該文件有文件名稱的,而且必須要有,所以叫做命名管道 mkfifo函數(shù) 輸入 man mkfifo 指令 制作一個 FIFOS ,表示命名管道 mkfifo fifo 制作一個管道

    2023年04月15日
    瀏覽(19)

覺得文章有用就打賞一下文章作者

支付寶掃一掃打賞

博客贊助

微信掃一掃打賞

請作者喝杯咖啡吧~博客贊助

支付寶掃一掃領取紅包,優(yōu)惠每天領

二維碼1

領取紅包

二維碼2

領紅包