這本免費的電子書使經驗豐富的程式設計師更深入了解 Linux 中進程間通訊(IPC)的核心概念和機制。
讓一個軟體流程與另一個軟體流程進行對話是一個微妙的平衡行為。但是,它對於應用程式而言可能是至關重要的功能,因此這是任何從事複雜專案的程式設計師都必須解決的問題。你的應用程式是否需要啟動由其它軟體處理的工作;監視外設或網路上正在執行的操作;或者檢測來自其它來源的信號,當你的軟體需要依賴其自身程式碼之外的東西來知道下一步做什麼或什麼時候做時,你就需要考慮進程間通訊(IPC)。
這在 Unix 作業系統上已經由來已久了,這可能是因為人們早期預期軟體會來自各種來源。按照相同的傳統,Linux 提供了一些同樣的 IPC 介面和一些新介面。Linux 核心具有多種 IPC 方法,util-linux 包包含了 ipcmk
、ipcrm
、ipcs
和 lsipc
命令,用於監視和管理 IPC 訊息。
在嘗試 IPC 之前,你應該知道系統上已經有哪些 IPC 設施。lsipc
命令提供了該資訊。
RESOURCE DESCRIPTION LIMIT USED USE%MSGMNI Number of message queues 32000 0 0.00%MSGMAX Max size of message (byt.. 8192 - -MSGMNB Default max size of queue 16384 - -SHMMNI Shared memory segments 4096 79 1.93%SHMALL Shared memory pages 184[...] 25452 0.00%SHMMAX Max size of shared memory 18446744073692774399SHMMIN Min size of shared memory 1 - -SEMMNI Number of semaphore ident 32000 0 0.00%SEMMNS Total number of semaphore 1024000.. 0 0.00%SEMMSL Max semaphores per semap 32000 - -SEMOPM Max number of operations p 500 - -SEMVMX Semaphore max value 32767 - -
你可能注意到,這個範例清單包含三種不同型別的 IPC 機制,每種機制在 Linux 核心中都是可用的:訊息(MSG)、共用記憶體(SHM)和號誌(SEM)。你可以用 ipcs
命令檢視每個子系統的當前活動:
$ ipcs------ Message Queues Creators/Owners ---msqid perms cuid cgid [...]------ Shared Memory Segment Creators/Ownersshmid perms cuid cgid [...]557056 700 seth users [...]3571713 700 seth users [...]2654210 600 seth users [...]2457603 700 seth users [...]------ Semaphore Arrays Creators/Owners ---semid perms cuid cgid [...]
這表明當前沒有訊息或號誌陣列,但是使用了一些共用記憶體段。
你可以在系統上執行一個簡單的範例,這樣就可以看到正在工作的系統之一。它涉及到一些 C 程式碼,所以你必須在系統上有構建工具。必須安裝這些軟體包才能從原始碼構建軟體,這些軟體包的名稱取決於發行版,因此請參考文件以獲取詳細資訊。例如,在基於 Debian 的發行版上,你可以在 wiki 的構建教學部分了解構建需求,而在基於 Fedora 的發行版上,你可以參考該文件的從原始碼安裝軟體部分。
你的系統已經有一個預設的訊息佇列,但是你可以使用 ipcmk
命令建立你自己的訊息佇列:
$ ipcmk --queueMessage queue id: 32764
編寫一個簡單的 IPC 訊息傳送器,為了簡單,在佇列 ID 中寫死:
#include <sys/ipc.h>#include <sys/msg.h>#include <stdio.h>#include <string.h>struct msgbuffer { char text[24];} message;int main() { int msqid = 32764; strcpy(message.text,"opensource.com"); msgsnd(msqid, &message, sizeof(message), 0); printf("Message: %s\n",message.text); printf("Queue: %d\n",msqid); return 0; }
編譯該應用程式並執行:
$ gcc msgsend.c -o msg.bin$ ./msg.binMessage: opensource.comQueue: 32769
你剛剛向你的訊息佇列傳送了一條訊息。你可以使用 ipcs
命令驗證這一點,可以使用 ——queue
選項將輸出限制到該訊息佇列:
$ ipcs -q------ Message Queues --------key msqid owner perms used-bytes messages0x7b341ab9 0 seth 666 0 00x72bd8410 32764 seth 644 24 1
你也可以檢索這些訊息:
#include <sys/ipc.h>#include <sys/msg.h>#include <stdio.h>struct msgbuffer { char text[24];} message;int main() { int msqid = 32764; msgrcv(msqid, &message, sizeof(message),0,0); printf("\nQueue: %d\n",msqid); printf("Got this message: %s\n", message.text); msgctl(msqid,IPC_RMID,NULL); return 0;
編譯並執行:
$ gcc get.c -o get.bin$ ./get.binQueue: 32764Got this message: opensource.com
這只是 Marty Kalin 的《Linux 進程間通訊指南》中課程的一個例子,可從 Opensource.com 下載的這本最新免費(且 CC 授權)的電子書。在短短的幾節課中,你將從訊息佇列、共用記憶體和號誌、通訊端、信號等中了解 IPC 的 POSIX 方法。認真閱讀 Marty 的書,你將成為一個博識的程式設計師。而這不僅適用於經驗豐富的編碼人員,如果你編寫的只是 shell 指令碼,那麼你將擁有有關管道(命名和未命名)和共用檔案的大量實踐知識,以及使用共用檔案或外部訊息佇列時需要了解的重要概念。
如果你對製作具有動態和具有系統感知的優秀軟體感興趣,那麼你需要了解 IPC。讓這本書做你的嚮導。