คิวข้อความมีการใช้งานในเคอร์เนล Linux อย่างไร


29

ฉันต้องการทราบว่า Message Queues ถูกนำไปใช้ในเคอร์เนล Linux อย่างไร


IPC_NOWAIT เราใช้เฉพาะในผู้รับ
Anwaar Qa

คำตอบ:


41

เคอร์เนล Linux (2.6) ใช้คิวข้อความสองคิว:
(แทนที่จะเป็น 'รายการข้อความ' เนื่องจากการนำไปใช้งานทำได้โดยการใช้รายการที่เชื่อมโยงโดยไม่ปฏิบัติตามหลักการ FIFO อย่างเคร่งครัด)

ข้อความ System V IPC

คิวข้อความจาก System V

กระบวนการสามารถเรียกใช้msgsnd()เพื่อส่งข้อความ เขาต้องผ่านตัวระบุ IPC ของคิวข้อความที่ได้รับขนาดของข้อความและโครงสร้างข้อความรวมถึงประเภทข้อความและข้อความ

ในด้านอื่น ๆ ที่จะเรียกกระบวนการmsgrcv()ที่จะได้รับข้อความผ่านตัวระบุ IPC ของคิวข้อความที่ข้อความควรจะได้รับการจัดเก็บขนาดและค่าที

tระบุข้อความที่ส่งคืนจากคิวค่าบวกหมายถึงข้อความแรกที่มีชนิดเท่ากับtถูกส่งคืนค่าลบส่งคืนข้อความสุดท้ายเท่ากับ type tและศูนย์ส่งคืนข้อความแรกของคิว

ฟังก์ชั่นเหล่านั้นถูกกำหนดไว้ในinclude / linux / msg.hและนำมาใช้ในipc / msg.c

มีข้อ จำกัด ตามขนาดของข้อความ (สูงสุด), จำนวนข้อความทั้งหมด (mni) และขนาดรวมของข้อความทั้งหมดในคิว (mnb):

$ sysctl kernel.msg{max,mni,mnb}
kernel.msgmax = 8192
kernel.msgmni = 1655
kernel.msgmnb = 16384

การส่งออกดังกล่าวข้างต้นมีที่มาจากอูบุนตู 10.10 ระบบค่าเริ่มต้นที่กำหนดไว้ในmsg.h

เพิ่มเติมอย่างไม่น่าเชื่อเก่า System V สิ่งคิวข้อความอธิบายที่นี่

POSIX คิวข้อความ

มาตรฐาน POSIX กำหนดกลไกการจัดคิวข้อความตามคิวข้อความของ System V IPC ซึ่งขยายโดยฟังก์ชันบางอย่าง:

  • อินเทอร์เฟซที่ใช้ไฟล์อย่างง่ายไปยังแอปพลิเคชัน
  • รองรับลำดับความสำคัญของข้อความ
  • รองรับการแจ้งเตือนแบบอะซิงโครนัส
  • หมดเวลาสำหรับการปิดกั้นการดำเนินงาน

ดูipc / mqueue.c

ตัวอย่าง

util-linux จัดเตรียมโปรแกรมบางอย่างสำหรับการวิเคราะห์และแก้ไขคิวข้อความและข้อมูลจำเพาะ POSIX แสดงตัวอย่าง C:

สร้างคิวข้อความด้วยipcmk; โดยทั่วไปคุณจะทำสิ่งนี้โดยการเรียกฟังก์ชัน C เช่นftok()และmsgget():

$ ipcmk -Q

ให้ดูว่าเกิดอะไรขึ้นกับการใช้ipcsหรือcat /proc/sysvipc/msg:

$ ipcs -q

------ Message Queues --------
key        msqid      owner      perms      used-bytes   messages    
0x33ec1686 65536      user       644        0            0           

ตอนนี้เติมคิวด้วยข้อความบางส่วน:

$ cat <<EOF >msg_send.c
#include <string.h>
#include <sys/msg.h> 

int main() {
  int msqid = 65536;
  struct message {
    long type;
    char text[20];
  } msg;

  msg.type = 1;
  strcpy(msg.text, "This is message 1");
  msgsnd(msqid, (void *) &msg, sizeof(msg.text), IPC_NOWAIT);
  strcpy(msg.text, "This is message 2");
  msgsnd(msqid, (void *) &msg, sizeof(msg.text), IPC_NOWAIT);

  return 0;
}
EOF

อีกครั้งคุณโดยทั่วไปจะไม่ฮาร์ดโค้ด msqid ในรหัส

$ gcc -o msg_send msg_send.c
$ ./msg_send
$ ipcs -q

------ Message Queues --------
key        msqid      owner      perms      used-bytes   messages    
0x33ec1686 65536      user       644        40           2        

และอีกด้านหนึ่งซึ่งจะได้รับข้อความ:

$ cat <<EOF >msg_recv.c
#include <stdio.h>
#include <sys/msg.h>

int main() {
  int msqid = 65536;
  struct message {
    long type;
    char text[20];
  } msg;
  long msgtyp = 0;

  msgrcv(msqid, (void *) &msg, sizeof(msg.text), msgtyp, MSG_NOERROR | IPC_NOWAIT);
  printf("%s \n", msg.text);

  return 0;
}
EOF

ดูว่าเกิดอะไรขึ้น:

$ gcc -o msg_recv msg_recv.c
$ ./msg_recv
This is message 1
$ ./msg_recv
This is message 2
$ ipcs -q

------ Message Queues --------
key        msqid      owner      perms      used-bytes   messages    
0x33ec1686 65536      user       644        0            0           

หลังจากได้รับสองคิวจะว่างเปล่าอีกครั้ง

ลบออกหลังจากนั้นโดยการระบุคีย์ ( -Q) หรือ msqid ( -q):

$ ipcrm -q 65536

ดังนั้นข้อความ (ประเภทและข้อความ) จึงถูกโคลน / คัดลอกจากนั้นสำเนานั้นจะถูกใส่ลงในคิวข้อความของระบบหรือไม่
trusktr

ใส่อย่างมาก ขอบคุณสำหรับคำอธิบายที่น่าอัศจรรย์นี้
User9102d82
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.