错误在消息队列示例中的realloc或free中

在这里,我收到一些问题在realloc or free的消息队列的例子。

在下面的程序中,从消息队列收到最后一条消息时,出现了double free or corruption错误。

我在消息队列中发送了10条消息,并且我在接收方收到了10条消息,并且工作正常。 收到每一条消息后,我正在释放buf指针。 而且它的每次都是免费的,但是上一次的问题就是第10次了。 它给定的错误,如double free or corruption如何可能之前,我检查它是NULL或不,它来了,如果条件意味着它不是NULL,那么它如何可以给这样的错误。

另外还有一件事让我感到惊讶,那就是当我跑了10条以上的消息的时候,它只会给出错误。

它的工作正常,如果我发送1到9个消息。

请让我知道我的代码确切的问题。

send.c

 /*filename : send.c *To compile : gcc send.c -o send */ #include <stdio.h> #include <stdlib.h> #include <errno.h> #include <string.h> #include <sys/types.h> #include <sys/ipc.h> #include <sys/msg.h> #define SEPRATOR 0X03 struct my_msgbuf { long mtype; /* Message type, must be > 0 */ char tag[10]; char messageType[5]; int messageNumber; char sender[64]; char formdata[1]; /* Some compilers allow `char mtext[0]` */ }; int main(void) { int msqid; key_t key; static int count = 0; int sperator = 3; int run = 1; if ((key = ftok("send.c", 'B')) == -1) { perror("ftok"); exit(1); } printf("send.c Key is = %d\n", key); if ((msqid = msgget(key, 0644 | IPC_CREAT)) == -1) { perror("msgget"); exit(1); } printf("Enter lines of text, ^D to quit:\n"); printf("Size of strcuture == %ld\n",sizeof (struct my_msgbuf)); while (run) { count++; /* Put string in a temporary place */ char tempformdata[1024]; char tempSender[64]; snprintf(tempformdata, sizeof (tempformdata), "%d%cHi hello test message here%c%d%cHi hello test message here%c%d%cHi hello test message here",count,SEPRATOR,SEPRATOR,count,SEPRATOR,SEPRATOR,count,SEPRATOR); snprintf(tempSender, sizeof (tempSender), "TESTMEM%cTESTMEM%cTESTMEM",SEPRATOR,SEPRATOR); /* +1 for the terminating '\0' */ size_t msgsz1 = strlen(tempformdata) + 1; //size_t msgsz2 = strlen(tempDestination) + 1; size_t msgsz2 = strlen(tempSender) + 1; /* Allocate structure, and memory for the string, in one go */ struct my_msgbuf *buf = malloc(sizeof (struct my_msgbuf) + msgsz1); /* Set up the message structure */ buf->mtype = 1; memcpy(buf->tag,"TAGVALUES",8); memcpy(buf->messageType,"FORM",4); buf->messageNumber = 5; memcpy(buf->formdata, tempformdata, msgsz1); memcpy(buf->sender, tempSender, strlen(tempSender)); /* And send the message */ msgsnd(msqid, buf, (sizeof (struct my_msgbuf) + msgsz1- sizeof(long)), 0); if (count == 11) run = 0; usleep(1000000); } if (msgctl(msqid, IPC_RMID, NULL) == -1) { perror("msgctl"); exit(1); } return 0; } 

receive.c

 /* filename : receive.c * To compile : gcc receive.c -o receive */ #include <stdio.h> #include <stdlib.h> #include <errno.h> #include <sys/types.h> #include <sys/ipc.h> #include <sys/msg.h> struct my_msgbuf { long mtype; /* Message type, must be > 0 */ char tag[10]; char messageType[5]; int messageNumber; char sender[64]; char formdata[1]; /* Some compilers allow `char mtext[0]` */ }; int main(void) { size_t msgsz = 8; struct my_msgbuf *buf = NULL; int msqid; key_t key; if ((key = ftok("send.c", 'B')) == -1) { /* same key as send.c */ perror("ftok"); exit(1); } if ((msqid = msgget(key, 0644)) == -1) { /* connect to the queue */ perror("msgget"); exit(1); } printf("test: ready to receive messages, captain.\n"); for (;;) { /* Allocate if `buf` is NULL, otherwise reallocate */ buf = realloc(buf, msgsz); /* Receive message */ ssize_t rsz = msgrcv(msqid, buf, msgsz, 1, 0); if (rsz == -1) { if (errno == E2BIG) msgsz += 8; /* Increase size to reallocate and try again */ else { perror("msgrcv"); break; } } else { /* Can use `buf->mtext` as a string, as it already is zero-terminated */ printf("Received message of length %d bytes\n", rsz); printf("\tReceived Tag value is : %s \n",buf->tag); printf("\tReceived Message Type value is : %s \n",buf->messageType); printf("\tReceived Message Number value is : %d \n",buf->messageNumber); printf("\tReceived destinations value is : %s \n",buf->sender); printf("\tReceived form Data Value is : %s \n",buf->formdata); if(buf!=NULL) { printf("\nFree Done in Else\n"); free(buf); printf("\nFree Done in Else 2 \n"); printf("test \n"); buf = NULL; } } } return 0; } 

输出:

 test: ready to receive messages, captain. Received message of length 175 bytes Received Tag value is : TAGVALUE Received Message Type value is : FORM Received Message Number value is : 5 Received destinations value is : TESTMEMTESTMEMTESTMEM Received form Data Value is : 1Hi hello test message here1Hi hello test message here1Hi hello test message here Free Done in Else Free Done in Else 2 test Received message of length 175 bytes Received Tag value is : TAGVALUE Received Message Type value is : FORM Received Message Number value is : 5 Received destinations value is : TESTMEMTESTMEMTESTMEM Received form Data Value is : 2Hi hello test message here2Hi hello test message here2Hi hello test message here Free Done in Else Free Done in Else 2 test . . . Received message of length 175 bytes Received Tag value is : TAGVALUE Received Message Type value is : FORM Received Message Number value is : 5 Received destinations value is : TESTMEMTESTMEMTESTMEM Received form Data Value is : 9Hi hello test message here9Hi hello test message here9Hi hello test message here Free Done in Else Free Done in Else 2 test msgrcv: Identifier removed quipment@ubuntu:~/main/IPC/message_queue$ ./receive test: ready to receive messages, captain. Received message of length 175 bytes Received Tag value is : TAGVALUE Received Message Type value is : FORM Received Message Number value is : 5 Received destinations value is : TESTMEMTESTMEMTESTMEM Received form Data Value is : 1Hi hello test message here1Hi hello test message here1Hi hello test message here Free Done in Else Free Done in Else 2 test Received message of length 175 bytes Received Tag value is : TAGVALUE Received Message Type value is : FORM Received Message Number value is : 5 Received destinations value is : TESTMEMTESTMEMTESTMEM Received form Data Value is : 2Hi hello test message here2Hi hello test message here2Hi hello test message here Free Done in Else Free Done in Else 2 test Received message of length 175 bytes Received Tag value is : TAGVALUE Received Message Type value is : FORM Received Message Number value is : 5 Received destinations value is : TESTMEMTESTMEMTESTMEM Received form Data Value is : 3Hi hello test message here3Hi hello test message here3Hi hello test message here Free Done in Else Free Done in Else 2 test Received message of length 175 bytes Received Tag value is : TAGVALUE Received Message Type value is : FORM Received Message Number value is : 5 Received destinations value is : TESTMEMTESTMEMTESTMEM Received form Data Value is : 4Hi hello test message here4Hi hello test message here4Hi hello test message here Free Done in Else Free Done in Else 2 test Received message of length 175 bytes Received Tag value is : TAGVALUE Received Message Type value is : FORM Received Message Number value is : 5 Received destinations value is : TESTMEMTESTMEMTESTMEM Received form Data Value is : 5Hi hello test message here5Hi hello test message here5Hi hello test message here Free Done in Else Free Done in Else 2 test Received message of length 175 bytes Received Tag value is : TAGVALUE Received Message Type value is : FORM Received Message Number value is : 5 Received destinations value is : TESTMEMTESTMEMTESTMEM Received form Data Value is : 6Hi hello test message here6Hi hello test message here6Hi hello test message here Free Done in Else Free Done in Else 2 test Received message of length 175 bytes Received Tag value is : TAGVALUE Received Message Type value is : FORM Received Message Number value is : 5 Received destinations value is : TESTMEMTESTMEMTESTMEM Received form Data Value is : 7Hi hello test message here7Hi hello test message here7Hi hello test message here Free Done in Else Free Done in Else 2 test Received message of length 175 bytes Received Tag value is : TAGVALUE Received Message Type value is : FORM Received Message Number value is : 5 Received destinations value is : TESTMEMTESTMEMTESTMEM Received form Data Value is : 8Hi hello test message here8Hi hello test message here8Hi hello test message here Free Done in Else Free Done in Else 2 test Received message of length 175 bytes Received Tag value is : TAGVALUE Received Message Type value is : FORM Received Message Number value is : 5 Received destinations value is : TESTMEMTESTMEMTESTMEM Received form Data Value is : 9Hi hello test message here9Hi hello test message here9Hi hello test message here Free Done in Else Free Done in Else 2 test Received message of length 178 bytes Received Tag value is : TAGVALUE Received Message Type value is : FORM Received Message Number value is : 5 Received destinations value is : TESTMEMTESTMEMTESTMEM Received form Data Value is : 10Hi hello test message here10Hi hello test message here10Hi hello test message here Free Done in Else *** glibc detected *** ./receive: double free or corruption (!prev): 0x0000000001b17010 *** ======= Backtrace: ========= /lib/libc.so.6(+0x775b6)[0x7f5faf6435b6] /lib/libc.so.6(cfree+0x73)[0x7f5faf649e83] ./receive[0x400986] /lib/libc.so.6(__libc_start_main+0xfd)[0x7f5faf5eac4d] ./receive[0x400719] ======= Memory map: ======== 00400000-00401000 r-xp 00000000 08:11 5374010 /home/quipment/main/IPC/message_queue/receive 00600000-00601000 r--p 00000000 08:11 5374010 /home/quipment/main/IPC/message_queue/receive 00601000-00602000 rw-p 00001000 08:11 5374010 /home/quipment/main/IPC/message_queue/receive 01b17000-01b38000 rw-p 00000000 00:00 0 [heap] 7f5fa8000000-7f5fa8021000 rw-p 00000000 00:00 0 7f5fa8021000-7f5fac000000 ---p 00000000 00:00 0 7f5faf3b5000-7f5faf3cb000 r-xp 00000000 08:01 2228303 /lib/libgcc_s.so.1 7f5faf3cb000-7f5faf5ca000 ---p 00016000 08:01 2228303 /lib/libgcc_s.so.1 7f5faf5ca000-7f5faf5cb000 r--p 00015000 08:01 2228303 /lib/libgcc_s.so.1 7f5faf5cb000-7f5faf5cc000 rw-p 00016000 08:01 2228303 /lib/libgcc_s.so.1 7f5faf5cc000-7f5faf746000 r-xp 00000000 08:01 2231881 /lib/libc-2.11.1.so 7f5faf746000-7f5faf945000 ---p 0017a000 08:01 2231881 /lib/libc-2.11.1.so 7f5faf945000-7f5faf949000 r--p 00179000 08:01 2231881 /lib/libc-2.11.1.so 7f5faf949000-7f5faf94a000 rw-p 0017d000 08:01 2231881 /lib/libc-2.11.1.so 7f5faf94a000-7f5faf94f000 rw-p 00000000 00:00 0 7f5faf94f000-7f5faf96f000 r-xp 00000000 08:01 2231874 /lib/ld-2.11.1.so 7f5fafb4b000-7f5fafb4e000 rw-p 00000000 00:00 0 7f5fafb6b000-7f5fafb6e000 rw-p 00000000 00:00 0 7f5fafb6e000-7f5fafb6f000 r--p 0001f000 08:01 2231874 /lib/ld-2.11.1.so 7f5fafb6f000-7f5fafb70000 rw-p 00020000 08:01 2231874 /lib/ld-2.11.1.so 7f5fafb70000-7f5fafb71000 rw-p 00000000 00:00 0 7fffab732000-7fffab747000 rw-p 00000000 00:00 0 [stack] 7fffab796000-7fffab797000 r-xp 00000000 00:00 0 [vdso] ffffffffff600000-ffffffffff601000 r-xp 00000000 00:00 0 [vsyscall] Aborted 

在receive.c中,应该按以下方式调用realloc:

 buf = realloc(buf, msgsz + sizeof(long)); 

这应该可以解决你的问题。

另外,在send.c文件中,你应该在每个msgsnd之后自由地调用,当把数据复制到tagmessageType字段时,你忘记了尾部的'\0'字符 – 你很幸运,因为内存被清零了,但是没有保证。