|
|
Message QueuesMessage Queues dienen zum Senden und Empfangen von Nachrichten. Eine solche Nachrichtenschlange kann mit Nachrichten verschiedenen Typs umgehen. Der Typ wird durch die Anwendung bestimmt und ist einfach eine Zahl. Ein Prozess kann Nachrichten an die Warteschlange senden. Beim Erreichen der Kapazität der Schlange kann der Prozess per Parameter bestimmen, ob er blockieren will bis die Nachricht abzuliefern ist oder lieber mit einem Fehler zurückkehren möchte. Auf der anderen Seite kann ein Prozess eine Nachricht bestimmten Typs anfordern. Auch hier steht es dem Programmierer frei, ob er möchte, dass der Prozess wartet, bis er eine passende Nachricht bekommt oder ob er mit einer Fehlermeldung sofort zurückkehren soll.
Die Funktion
#include <sys/ipc.h> #include <sys/msg.h> int msgget(key_t key, int msgflg); Der Parameter key ist entweder eine Schlüsselzahl oder IPC_PRIVATE. Der Parameter msgflg kombiniert die Konstanten IPC_CREAT und IPC_EXCL und neun Berechtigungsbits für den Eigner, die Gruppe und der Welt, wie sie von chmod verwendet werden, indem sie mit dem senkrechten Strich geodert werden. Der Rückgabewert ist -1 im Fehlerfall oder die Message Queue ID, die für die nächsten Aufrufe benötigt wird.
Die Funktionen
struct msgbuf { long mtype; /* von der Anwendung definierbar > 0 */ char mtext[1]; /* Nachrichtendaten beginnen hier */ }; Es kann als Typ eine beliebige Zahl größer Null verwendet werden, die allein von der Applikation festgelegt werden. Auf diese Weise können Sie leicht verschiedene Arten von Daten austauschen und sie über den Nachrichtentyp trennen. Für die eigenen Nachrichten werden Sie im mtext vermutlich mehr als ein Zeichen versenden wollen. Dazu definieren Sie sich eine eigene Struktur mit entsprechend größerem Datenpuffer. Die Größe wird beiden Funktionen als Parameter übergeben.
Mit der Funktion
#include <sys/ipc.h> #include <sys/msg.h> int msgsnd(int msqid, struct msgbuf *msgp, size_t msgsz, int msgflg);
Der erste Parameter ist der Rückgabewert der Funktion
Mit der Funktion
#include <sys/ipc.h> #include <sys/msg.h> int msgrcv(int msqid, struct msgbuf *msgp, size_t msgsz, long msgtyp, int msgflg);
Der erste Parameter ist der Rückgabewert der Funktion
Mit der Funktion
#include <sys/ipc.h> #include <sys/msg.h> int msgctl(int msqid, int kommando, struct msqid_ds *buf); Als Paramter kommando können folgende Konstanten übergeben werden:
[Message Kontrollkommandos]L|L
Konstante & Bedeutung
Mit dem Kommando
BeispielDas Programm rcvmsg.c wartet auf eine Nachricht in einer Message Queue. Die Nummer des Typs wird als erster Parameter beim Aufruf übergeben. Wird nichts übergeben wartet das Programm auf eine beliebige Nachricht.
[Empfange Nachricht rcvmsg.c] #include <sys/ipc.h> #include <sys/msg.h>
#define MSGSIZE 20
int main(int argc, char **argv) { int msgID; struct myMsg { long mtype; char mtext[MSGSIZE]; } dataMsg; long msgTyp = 0;
/* hole die Messagetypnummer aus dem ersten Parameter */ if (argc>1) { msgTyp = atol(argv[1]); }
/* Messagequeue oeffnen bzw. erzeugen */ msgID = msgget(2404, IPC_CREAT | 0666); if (msgID >= 0) { printf("Warte auf Message Type %ldn", msgTyp); if (-1==msgrcv(msgID, &dataMsg, MSGSIZE, msgTyp, 0)) { perror("msgrcv"); /* Fehler */ } else { /* Wir sind durchglaufen */ printf("Daten empfangen: %sn", dataMsg.mtext); } } else { perror("msgget"); } }
Das Programm sndmsg.c sendet Nachrichten. Der Nachrichtentyp wird wie
bei rcvmsg.c als erster Parameter übergeben. Als zweiter Parameter
kann ein
String übergeben werden, der dann als Daten in der Messages Queue abgestellt
wird und den
[Sende Nachrichten sndmsg.c] #include <sys/ipc.h> #include <sys/msg.h>
#define MSGSIZE 20
int main(int argc, char **argv) { int msgID; struct myMsg { long mtype; char mtext[MSGSIZE]; } dataMsg; long msgTyp = 0;
/* hole die Messagetypnummer aus dem ersten Parameter */ if (argc>1) { dataMsg.mtype = atol(argv[1]); } if (argc>2) { strncpy(dataMsg.mtext, argv[2], MSGSIZE); } else { *dataMsg.mtext = 0; } /* Messagequeue oeffnen bzw. erzeugen */ msgID = msgget(2404, IPC_CREAT | 0666); if (msgID >= 0) { printf("Sende Messagetyp %ldn", dataMsg.mtype); if (-1==msgsnd(msgID, &dataMsg, MSGSIZE, 0)) { perror("msgsnd"); /* Fehler */ } else { /* Wir sind durchglaufen */ printf("Daten gesendet: %sn", dataMsg.mtext); } } else { perror("msgget"); } } Mit Hilfe der beiden Programme läßt sich das Verhalten der Message Queue leicht testen. Eine Anpassung an eigene Befürfnisse dürfte eine leichte Übung sein.
Die Message Queue bleibt solange erhalten, bis ein Programm sie explizit
per
|
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|