ftok函数
ftok - convert a pathname and a project identifier to a System V IPC key
SYNOPSIS
#include <sys/types.h>
#include <sys/ipc.h>
key_t ftok(const char *pathname, int proj_id);
DESCRIPTION
The ftok() function uses the identity of the file named by the given pathname
(which must refer to an existing, accessible file) and the least significant 8
bits of proj_id (which must be nonzero) to generate a key_t type System V IPC
key, suitable for use with msgget(2), semget(2), or shmget(2).
The resulting value is the same for all pathnames that name the same file, when
the same value of proj_id is used. The value returned should be different when
the (simultaneously existing) files or the project IDs differ.
RETURN VALUE
On success, the generated key_t value is returned. On failure -1 is returned,
with errno indicating the error as for the stat(2) system call.
ATTRIBUTES
For an explanation of the terms used in this section, see attributes(7).
测试一:生成一个键值:
#include <iostream>
#include <unistd.h>
#include <stdlib.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <string.h>
#include <stdio.h>
#include <stdint.h>
#include <linux/limits.h>
#include <fcntl.h>
#include <sys/ipc.h>
#define DEBUG_INFO(format, ...) printf("%s:%d -- " format "\n", __func__, __LINE__,##__VA_ARGS__)
using namespace std;
struct mymsg{
long mtype;
int len;
int frame_size;
int frame_index;
int frame_count;
int offset;
int length;
char buf[PIPE_BUF];
uint32_t crc;
};
int main(int argc, char **argv)
{
system("mkdir /home/lkmao/test/msg/ -p");
key_t key = ftok("/home/lkmao/test/msg/",'a');
if(key == -1){
perror("ftok");
exit(-1);
}
DEBUG_INFO("%d %x",key,key);
system("ls -lsh /home/lkmao/test/msg/");
DEBUG_INFO("msg queue test");
return 0;
}
测试结果:
main:36 -- 1627471003 61013c9b
总用量 0
main:38 -- msg queue test
msgget()函数
NAME
msgget - get a System V message queue identifier
SYNOPSIS
#include <sys/types.h>
#include <sys/ipc.h>
#include <sys/msg.h>
int msgget(key_t key, int msgflg);
msgsnd()函数和msgrcv
NAME
msgrcv, msgsnd - System V message queue operations
SYNOPSIS
#include <sys/types.h>
#include <sys/ipc.h>
#include <sys/msg.h>
int msgsnd(int msqid, const void *msgp, size_t msgsz, int msgflg);
ssize_t msgrcv(int msqid, void *msgp, size_t msgsz, long msgtyp,
int msgflg);
测试二,子进程发消息,父进程接收消息
#include <iostream>
#include <unistd.h>
#include <stdlib.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <string.h>
#include <stdio.h>
#include <stdint.h>
#include <linux/limits.h>
#include <fcntl.h>
#include <sys/ipc.h>
#include <sys/msg.h>
#define DEBUG_INFO(format, ...) printf("%s:%d -- " format "\n", __func__, __LINE__,##__VA_ARGS__)
using namespace std;
struct mymsg{
long mtype;
int len;
int frame_size;
int frame_index;
int frame_count;
int offset;
int length;
char buf[PIPE_BUF];
uint32_t crc;
};
int main(int argc, char **argv)
{
system("rm -rf /home/lkmao/test/msg/");
system("mkdir /home/lkmao/test/msg/ -p");
key_t key = ftok("/home/lkmao/test/msg/",'a');
if(key == -1){
perror("ftok");
exit(-1);
}
DEBUG_INFO("key %d %x",key,key);
system("ls -lsah /home/lkmao/test/msg/");
//msgget(key,IPC_CREAT | IPC_EXCL);//不存在则创建,IPC_CREAT加IPC_EXCL以后表表示存在则报错
//int msg_id = msgget(key,IPC_CREAT);//大于0的32位整数:视参数msgflg来确定操作。通常要求此值来源于ftok返回的IPC键值
int msg_id = msgget(IPC_PRIVATE,IPC_CREAT | 0666);//0(IPC_PRIVATE):会建立新的消息队列
if(msg_id == -1){
perror("msgget");
exit(-1);
}
DEBUG_INFO("msg_id = %d %x",msg_id,msg_id);
system("ls -lsh /home/lkmao/test/msg/");
pid_t pid = fork();
if(pid == -1){
perror("fork");
exit(-1);
}
if(pid == 0){
struct mymsg *pmsg = (struct mymsg*)malloc(sizeof(struct mymsg));
pmsg->mtype = 0x1001;
pmsg->crc = 0x2001;
//msgsnd(msg_id,pmsg,sizeof(struct mymsg) - sizeof(long),IPC_NOWAIT); //不阻塞
int ret = msgsnd(msg_id,pmsg,sizeof(struct mymsg) - sizeof(long),0);//阻塞
if(ret == -1){
perror("msgsnd");
free(pmsg);
exit(-1);
}
DEBUG_INFO("ret = %d",ret);
sleep(1);
free(pmsg);
}
if(pid > 0){
sleep(2);
struct mymsg *pmsg = (struct mymsg*)malloc(sizeof(struct mymsg));
//pmsg->mtype = 0x1001;
//int ret = msgrcv(msg_id,pmsg,sizeof(struct mymsg) - sizeof(long),0x1001,0);
int ret = msgrcv(msg_id,pmsg,sizeof(struct mymsg) - sizeof(long),0,0);
if(ret == -1){
perror("msgrcv");
free(pmsg);
exit(-1);
}
DEBUG_INFO("msgrcv:%x,%x,",pmsg->mtype,pmsg->crc);
free(pmsg);
}
DEBUG_INFO("msg queue test finish");
return 0;
}
测试结果:
main:38 -- key 1627471003 61013c9b
总用量 8.0K
4.0K drwxrwxr-x 2 lkmao lkmao 4.0K 5月 8 15:37 .
4.0K drwxrwxr-x 12 lkmao lkmao 4.0K 5月 8 15:37 ..
main:48 -- msg_id = 196614 30006
总用量 0
main:66 -- ret = 0
main:83 -- msg queue test
main:78 -- msgrcv:1001,2001,
main:83 -- msg queue test
msgctl函数
NAME
msgctl - System V message control operations
SYNOPSIS
#include <sys/types.h>
#include <sys/ipc.h>
#include <sys/msg.h>
int msgctl(int msqid, int cmd, struct msqid_ds *buf);
msqid_ds结构体:
struct msqid_ds {
struct ipc_perm msg_perm; /* Ownership and permissions */
time_t msg_stime; /* Time of last msgsnd(2) */
time_t msg_rtime; /* Time of last msgrcv(2) */
time_t msg_ctime; /* Time of last change */
unsigned long __msg_cbytes; /* Current number of bytes in
queue (nonstandard) */
msgqnum_t msg_qnum; /* Current number of messages
in queue */
msglen_t msg_qbytes; /* Maximum number of bytes
allowed in queue */
pid_t msg_lspid; /* PID of last msgsnd(2) */
pid_t msg_lrpid; /* PID of last msgrcv(2) */
};
struct ipc_perm
struct ipc_perm {
key_t __key; /* Key supplied to msgget(2) */
uid_t uid; /* Effective UID of owner */
gid_t gid; /* Effective GID of owner */
uid_t cuid; /* Effective UID of creator */
gid_t cgid; /* Effective GID of creator */
unsigned short mode; /* Permissions */
unsigned short __seq; /* Sequence number */
};
测试代码:获取msgget之后、msgsnd之后、msgrcv之后的消息的属性。
#include <iostream>
#include <unistd.h>
#include <stdlib.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <string.h>
#include <stdio.h>
#include <stdint.h>
#include <linux/limits.h>
#include <fcntl.h>
#include <sys/ipc.h>
#include <sys/msg.h>
#define DEBUG_INFO(format, ...) printf("%s:%d -- " format "\n", __func__, __LINE__,##__VA_ARGS__)
using namespace std;
struct mymsg{
long mtype;
int len;
int frame_size;
int frame_index;
int frame_count;
int offset;
int length;
char buf[PIPE_BUF];
uint32_t crc;
};
void show_msg_queue_attr(int msg_id,struct msqid_ds *pmsg_info){
int ret = -1;
struct msqid_ds msg_info;
ret = msgctl(msg_id,IPC_STAT,&msg_info);
if(ret == -1){
perror("msgctl IPC_STAT");
exit(-1);
}
DEBUG_INFO("%ld",msg_info.msg_cbytes);
DEBUG_INFO("%d",msg_info.msg_qnum);
DEBUG_INFO("%d",msg_info.msg_qbytes);
DEBUG_INFO("%d",msg_info.msg_lspid);
DEBUG_INFO("%d",msg_info.msg_lrpid);
DEBUG_INFO("%s",ctime(&msg_info.msg_stime));
DEBUG_INFO("%s",ctime(&msg_info.msg_rtime));
DEBUG_INFO("%s",ctime(&msg_info.msg_ctime));
DEBUG_INFO("%d",msg_info.msg_perm.uid);
DEBUG_INFO("%d",msg_info.msg_perm.gid);
if(pmsg_info != NULL){
memcpy(pmsg_info,&msg_info,sizeof(msg_info));
}
}
int main(int argc, char **argv)
{
system("rm -rf /home/lkmao/test/msg/");
system("mkdir /home/lkmao/test/msg/ -p");
key_t key = ftok("/home/lkmao/test/msg/",'a');
if(key == -1){
perror("ftok");
exit(-1);
}
DEBUG_INFO("key %d %x",key,key);
system("ls -lsah /home/lkmao/test/msg/");
//msgget(key,IPC_CREAT | IPC_EXCL);//不存在则创建,IPC_CREAT加IPC_EXCL以后表表示存在则报错
//int msg_id = msgget(key,IPC_CREAT);//大于0的32位整数:视参数msgflg来确定操作。通常要求此值来源于ftok返回的IPC键值
int msg_id = msgget(IPC_PRIVATE,IPC_CREAT | 0666);//0(IPC_PRIVATE):会建立新的消息队列
if(msg_id == -1){
perror("msgget");
exit(-1);
}
show_msg_queue_attr(msg_id,NULL);
DEBUG_INFO("msg_id = %d %x",msg_id,msg_id);
system("ls -lsh /home/lkmao/test/msg/");
pid_t pid = fork();
if(pid == -1){
perror("fork");
exit(-1);
}
if(pid == 0){
struct mymsg *pmsg = (struct mymsg*)malloc(sizeof(struct mymsg));
pmsg->mtype = 0x1001;
pmsg->crc = 0x2001;
//msgsnd(msg_id,pmsg,sizeof(struct mymsg) - sizeof(long),IPC_NOWAIT); //不阻塞
int ret = msgsnd(msg_id,pmsg,sizeof(struct mymsg) - sizeof(long),0);//阻塞
if(ret == -1){
perror("msgsnd");
free(pmsg);
exit(-1);
}
DEBUG_INFO("ret = %d",ret);
show_msg_queue_attr(msg_id,NULL);
sleep(1);
free(pmsg);
}
if(pid > 0){
sleep(2);
struct mymsg *pmsg = (struct mymsg*)malloc(sizeof(struct mymsg));
//pmsg->mtype = 0x1001;
//int ret = msgrcv(msg_id,pmsg,sizeof(struct mymsg) - sizeof(long),0x1001,0);
int ret = msgrcv(msg_id,pmsg,sizeof(struct mymsg) - sizeof(long),0,0);
if(ret == -1){
perror("msgrcv");
free(pmsg);
exit(-1);
}
show_msg_queue_attr(msg_id,NULL);
DEBUG_INFO("msgrcv:%x,%x,",pmsg->mtype,pmsg->crc);
free(pmsg);
}
DEBUG_INFO("msg queue test finish");
return 0;
}
输出结果:
main:66 -- key 1627471003 61013c9b
总用量 8.0K
4.0K drwxrwxr-x 2 lkmao lkmao 4.0K 5月 8 16:06 .
4.0K drwxrwxr-x 12 lkmao lkmao 4.0K 5月 8 16:06 ..
show_msg_queue_attr:38 -- 0
show_msg_queue_attr:39 -- 0
show_msg_queue_attr:41 -- 16384
show_msg_queue_attr:42 -- 0
show_msg_queue_attr:43 -- 0
show_msg_queue_attr:45 -- Thu Jan 1 08:00:00 1970
show_msg_queue_attr:46 -- Thu Jan 1 08:00:00 1970
show_msg_queue_attr:47 -- Mon May 8 16:06:54 2023
show_msg_queue_attr:49 -- 1000
show_msg_queue_attr:50 -- 1000
main:77 -- msg_id = 360459 5800b
总用量 0
main:96 -- ret = 0
show_msg_queue_attr:38 -- 4128
show_msg_queue_attr:39 -- 1
show_msg_queue_attr:41 -- 16384
show_msg_queue_attr:42 -- 56349
show_msg_queue_attr:43 -- 0
show_msg_queue_attr:45 -- Mon May 8 16:06:54 2023
show_msg_queue_attr:46 -- Thu Jan 1 08:00:00 1970
show_msg_queue_attr:47 -- Mon May 8 16:06:54 2023
show_msg_queue_attr:49 -- 1000
show_msg_queue_attr:50 -- 1000
main:117 -- msg queue test finish
show_msg_queue_attr:38 -- 0
show_msg_queue_attr:39 -- 0
show_msg_queue_attr:41 -- 16384
show_msg_queue_attr:42 -- 56349
show_msg_queue_attr:43 -- 56340
show_msg_queue_attr:45 -- Mon May 8 16:06:54 2023
show_msg_queue_attr:46 -- Mon May 8 16:06:56 2023
show_msg_queue_attr:47 -- Mon May 8 16:06:54 2023
show_msg_queue_attr:49 -- 1000
show_msg_queue_attr:50 -- 1000
main:113 -- msgrcv:1001,2001,
main:117 -- msg queue test finish
删除消息队列IPC_RMID
测试三,删除测试。
#include <iostream>
#include <unistd.h>
#include <stdlib.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <string.h>
#include <stdio.h>
#include <stdint.h>
#include <linux/limits.h>
#include <fcntl.h>
#include <sys/ipc.h>
#include <sys/msg.h>
#define DEBUG_INFO(format, ...) printf("%s:%d -- " format "\n", __func__, __LINE__,##__VA_ARGS__)
using namespace std;
struct mymsg{
long mtype;
int len;
int frame_size;
int frame_index;
int frame_count;
int offset;
int length;
char buf[PIPE_BUF];
uint32_t crc;
};
void show_msg_queue_attr(int msg_id,struct msqid_ds *pmsg_info){
int ret = -1;
struct msqid_ds msg_info;
ret = msgctl(msg_id,IPC_STAT,&msg_info);
if(ret == -1){
perror("msgctl IPC_STAT");
exit(-1);
}
DEBUG_INFO("%ld",msg_info.msg_cbytes);
DEBUG_INFO("%d",msg_info.msg_qnum);
DEBUG_INFO("%d",msg_info.msg_qbytes);
DEBUG_INFO("%d",msg_info.msg_lspid);
DEBUG_INFO("%d",msg_info.msg_lrpid);
DEBUG_INFO("%s",ctime(&msg_info.msg_stime));
DEBUG_INFO("%s",ctime(&msg_info.msg_rtime));
DEBUG_INFO("%s",ctime(&msg_info.msg_ctime));
DEBUG_INFO("%d",msg_info.msg_perm.uid);
DEBUG_INFO("%d",msg_info.msg_perm.gid);
if(pmsg_info != NULL){
memcpy(pmsg_info,&msg_info,sizeof(msg_info));
}
}
int main(int argc, char **argv)
{
system("rm -rf /home/lkmao/test/msg/");
system("mkdir /home/lkmao/test/msg/ -p");
key_t key = ftok("/home/lkmao/test/msg/",'a');
if(key == -1){
perror("ftok");
exit(-1);
}
DEBUG_INFO("key %d %x",key,key);
system("ls -lsah /home/lkmao/test/msg/");
//msgget(key,IPC_CREAT | IPC_EXCL);//不存在则创建,IPC_CREAT加IPC_EXCL以后表表示存在则报错
int msg_id = msgget(key,IPC_CREAT | 0666);//大于0的32位整数:视参数msgflg来确定操作。通常要求此值来源于ftok返回的IPC键值
//int msg_id = msgget(IPC_PRIVATE,IPC_CREAT | 0666);//0(IPC_PRIVATE):会建立新的消息队列
if(msg_id == -1){
perror("msgget");
exit(-1);
}
struct msqid_ds msg_info;
show_msg_queue_attr(msg_id,&msg_info);
int ret = msgget(key,IPC_CREAT | IPC_EXCL | 0666);
if(ret == -1){
perror("msgget");
DEBUG_INFO("delete msg");
if(msgctl(msg_id,IPC_RMID,&msg_info) == 0){
DEBUG_INFO("delete msg ok");
}
}else{
}
ret = msgget(key,IPC_CREAT | IPC_EXCL | 0666);
if(ret == -1){
perror("msgget");
msgctl(msg_id,IPC_RMID,&msg_info);
}else{
DEBUG_INFO("msgget ok = %d",msg_id);
}
DEBUG_INFO("msg queue test finish");
return 0;
}
测试结果:
main:66 -- key 1627471003 61013c9b
总用量 8.0K
4.0K drwxrwxr-x 2 lkmao lkmao 4.0K 5月 8 16:30 .
4.0K drwxrwxr-x 12 lkmao lkmao 4.0K 5月 8 16:30 ..
show_msg_queue_attr:38 -- 0
show_msg_queue_attr:39 -- 0
show_msg_queue_attr:41 -- 16384
show_msg_queue_attr:42 -- 0
show_msg_queue_attr:43 -- 0
show_msg_queue_attr:45 -- Thu Jan 1 08:00:00 1970
show_msg_queue_attr:46 -- Thu Jan 1 08:00:00 1970
show_msg_queue_attr:47 -- Mon May 8 16:29:33 2023
show_msg_queue_attr:49 -- 1000
show_msg_queue_attr:50 -- 1000
msgget: File exists
main:82 -- delete msg
main:84 -- delete msg ok
main:95 -- msgget ok = 65536
main:98 -- msg queue test finish
IPC_SET
小结
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)