0 | |
diff --git a/src/pl-thread.c b/src/pl-thread.c
|
1 | |
index 19c2484..9feaf0b 100644
|
2 | |
--- a/src/pl-thread.c
|
3 | |
+++ b/src/pl-thread.c
|
4 | |
@@ -2773,9 +2773,11 @@ running. The thread may pick a message containing an atom from the
|
5 | |
queue, which now has not been marked and is no longer part of the
|
6 | |
queue, so it isn't marked in the queue either.
|
7 | |
|
8 | |
-Note that we only need this for queues that are not associated to
|
9 | |
-threads. Those associated with a thread mark both the stacks and the
|
10 | |
-queue in one pass, marking the atoms in either.
|
11 | |
+Originally, I thought we only need this for queues that are not
|
12 | |
+associated to threads. Those associated with a thread mark both the
|
13 | |
+stacks and the queue in one pass, marking the atoms in either. However,
|
14 | |
+we also need to lock to avoid get_message() destroying the record while
|
15 | |
+markAtomsMessageQueue() scans it. This fixes the reopened Bug#142.
|
16 | |
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
|
17 | |
|
18 | |
static int
|
19 | |
@@ -2827,13 +2829,10 @@ get_message(message_queue *queue, term_t msg, struct timespec *deadline ARG_LD)
|
20 | |
if ( rc )
|
21 | |
{ DEBUG(MSG_QUEUE, Sdprintf("%d: match\n", PL_thread_self()));
|
22 | |
|
23 | |
- if (GD->atoms.gc_active)
|
24 | |
- markAtomsRecord(msgp->message);
|
25 | |
+ if (GD->atoms.gc_active)
|
26 | |
+ markAtomsRecord(msgp->message);
|
27 | |
|
28 | |
-#ifdef O_ATOMGC
|
29 | |
- if ( queue->type == QTYPE_QUEUE )
|
30 | |
- simpleMutexLock(&queue->gc_mutex);
|
31 | |
-#endif
|
32 | |
+ simpleMutexLock(&queue->gc_mutex); /* see (*) */
|
33 | |
if ( prev )
|
34 | |
{ if ( !(prev->next = msgp->next) )
|
35 | |
queue->tail = prev;
|
36 | |
@@ -2841,10 +2840,8 @@ get_message(message_queue *queue, term_t msg, struct timespec *deadline ARG_LD)
|
37 | |
{ if ( !(queue->head = msgp->next) )
|
38 | |
queue->tail = NULL;
|
39 | |
}
|
40 | |
-#ifdef O_ATOMGC
|
41 | |
- if ( queue->type == QTYPE_QUEUE )
|
42 | |
- simpleMutexUnlock(&queue->gc_mutex);
|
43 | |
-#endif
|
44 | |
+ simpleMutexUnlock(&queue->gc_mutex);
|
45 | |
+
|
46 | |
free_thread_message(msgp);
|
47 | |
queue->size--;
|
48 | |
if ( queue->wait_for_drain )
|